Commit e02f51762f

Austin Rude <rudedogg@users.noreply.github.com>
2022-08-06 00:01:57
autodoc: Run through prettier formatter with default settings
1 parent 18440cb
Changed files (1)
lib
docs
lib/docs/main.js
@@ -1,3259 +1,3388 @@
-'use strict';
+"use strict";
 
 var zigAnalysis;
 
-(function() {
-    let domStatus = (document.getElementById("status"));
-    let domSectNav = (document.getElementById("sectNav"));
-    let domListNav = (document.getElementById("listNav"));
-    let domSectMainPkg = (document.getElementById("sectMainPkg"));
-    let domSectPkgs = (document.getElementById("sectPkgs"));
-    let domListPkgs = (document.getElementById("listPkgs"));
-    let domSectTypes = (document.getElementById("sectTypes"));
-    let domListTypes = (document.getElementById("listTypes"));
-    let domSectTests = (document.getElementById("sectTests"));
-    let domListTests = (document.getElementById("listTests"));
-    let domSectNamespaces = (document.getElementById("sectNamespaces"));
-    let domListNamespaces = (document.getElementById("listNamespaces"));
-    let domSectErrSets = (document.getElementById("sectErrSets"));
-    let domListErrSets = (document.getElementById("listErrSets"));
-    let domSectFns = (document.getElementById("sectFns"));
-    let domListFns = (document.getElementById("listFns"));
-    let domSectFields = (document.getElementById("sectFields"));
-    let domListFields = (document.getElementById("listFields"));
-    let domSectGlobalVars = (document.getElementById("sectGlobalVars"));
-    let domListGlobalVars = (document.getElementById("listGlobalVars"));
-    let domSectValues = (document.getElementById("sectValues"));
-    let domListValues = (document.getElementById("listValues"));
-    let domFnProto = (document.getElementById("fnProto"));
-    let domFnProtoCode = (document.getElementById("fnProtoCode"));
-    let domSectParams = (document.getElementById("sectParams"));
-    let domListParams = (document.getElementById("listParams"));
-    let domTldDocs = (document.getElementById("tldDocs"));
-    let domSectFnErrors = (document.getElementById("sectFnErrors"));
-    let domListFnErrors = (document.getElementById("listFnErrors"));
-    let domTableFnErrors =(document.getElementById("tableFnErrors"));
-    let domFnErrorsAnyError = (document.getElementById("fnErrorsAnyError"));
-    let domFnExamples = (document.getElementById("fnExamples"));
-    // let domListFnExamples = (document.getElementById("listFnExamples"));
-    let domFnNoExamples = (document.getElementById("fnNoExamples"));
-    let domDeclNoRef = (document.getElementById("declNoRef"));
-    let domSearch = (document.getElementById("search"));
-    let domSectSearchResults = (document.getElementById("sectSearchResults"));
-
-    let domListSearchResults = (document.getElementById("listSearchResults"));
-    let domSectSearchNoResults = (document.getElementById("sectSearchNoResults"));
-    let domSectInfo = (document.getElementById("sectInfo"));
-    // let domTdTarget = (document.getElementById("tdTarget"));
-    let domPrivDeclsBox = (document.getElementById("privDeclsBox"));
-    let domTdZigVer = (document.getElementById("tdZigVer"));
-    let domHdrName = (document.getElementById("hdrName"));
-    let domHelpModal = (document.getElementById("helpDialog"));
-
-    
-    let searchTimer = null;
-
-    
-    let escapeHtmlReplacements = { "&": "&amp;", '"': "&quot;", "<": "&lt;", ">": "&gt;" };
-
-    let typeKinds = (indexTypeKinds());
-    let typeTypeId =  (findTypeTypeId());
-    let pointerSizeEnum = { One: 0, Many: 1, Slice: 2, C: 3 };
-
-    // for each package, is an array with packages to get to this one
-    let canonPkgPaths = computeCanonicalPackagePaths();
-
-    
-
-    // for each decl, is an array with {declNames, pkgNames} to get to this one
-    
-    let canonDeclPaths = null; // lazy; use getCanonDeclPath
-
-    // for each type, is an array with {declNames, pkgNames} to get to this one
-    
-    let canonTypeDecls = null; // lazy; use getCanonTypeDecl
-
-    
-
-    
-    let curNav = {
-        showPrivDecls: false,
-        // each element is a package name, e.g. @import("a") then within there @import("b")
-        // starting implicitly from root package
-        pkgNames: [],
-        // same as above except actual packages, not names
-        pkgObjs: [],
-        // Each element is a decl name, `a.b.c`, a is 0, b is 1, c is 2, etc.
-        // empty array means refers to the package itself
-        declNames: [],
-        // these will be all types, except the last one may be a type or a decl
-        declObjs: [],
-
-        // (a, b, c, d) comptime call; result is the value the docs refer to
-        callName: null,
-    };
-
-    let curNavSearch = "";
-    let curSearchIndex = -1;
-    let imFeelingLucky = false;
+(function () {
+  let domStatus = document.getElementById("status");
+  let domSectNav = document.getElementById("sectNav");
+  let domListNav = document.getElementById("listNav");
+  let domSectMainPkg = document.getElementById("sectMainPkg");
+  let domSectPkgs = document.getElementById("sectPkgs");
+  let domListPkgs = document.getElementById("listPkgs");
+  let domSectTypes = document.getElementById("sectTypes");
+  let domListTypes = document.getElementById("listTypes");
+  let domSectTests = document.getElementById("sectTests");
+  let domListTests = document.getElementById("listTests");
+  let domSectNamespaces = document.getElementById("sectNamespaces");
+  let domListNamespaces = document.getElementById("listNamespaces");
+  let domSectErrSets = document.getElementById("sectErrSets");
+  let domListErrSets = document.getElementById("listErrSets");
+  let domSectFns = document.getElementById("sectFns");
+  let domListFns = document.getElementById("listFns");
+  let domSectFields = document.getElementById("sectFields");
+  let domListFields = document.getElementById("listFields");
+  let domSectGlobalVars = document.getElementById("sectGlobalVars");
+  let domListGlobalVars = document.getElementById("listGlobalVars");
+  let domSectValues = document.getElementById("sectValues");
+  let domListValues = document.getElementById("listValues");
+  let domFnProto = document.getElementById("fnProto");
+  let domFnProtoCode = document.getElementById("fnProtoCode");
+  let domSectParams = document.getElementById("sectParams");
+  let domListParams = document.getElementById("listParams");
+  let domTldDocs = document.getElementById("tldDocs");
+  let domSectFnErrors = document.getElementById("sectFnErrors");
+  let domListFnErrors = document.getElementById("listFnErrors");
+  let domTableFnErrors = document.getElementById("tableFnErrors");
+  let domFnErrorsAnyError = document.getElementById("fnErrorsAnyError");
+  let domFnExamples = document.getElementById("fnExamples");
+  // let domListFnExamples = (document.getElementById("listFnExamples"));
+  let domFnNoExamples = document.getElementById("fnNoExamples");
+  let domDeclNoRef = document.getElementById("declNoRef");
+  let domSearch = document.getElementById("search");
+  let domSectSearchResults = document.getElementById("sectSearchResults");
+
+  let domListSearchResults = document.getElementById("listSearchResults");
+  let domSectSearchNoResults = document.getElementById("sectSearchNoResults");
+  let domSectInfo = document.getElementById("sectInfo");
+  // let domTdTarget = (document.getElementById("tdTarget"));
+  let domPrivDeclsBox = document.getElementById("privDeclsBox");
+  let domTdZigVer = document.getElementById("tdZigVer");
+  let domHdrName = document.getElementById("hdrName");
+  let domHelpModal = document.getElementById("helpDialog");
+
+  let searchTimer = null;
+
+  let escapeHtmlReplacements = {
+    "&": "&amp;",
+    '"': "&quot;",
+    "<": "&lt;",
+    ">": "&gt;",
+  };
+
+  let typeKinds = indexTypeKinds();
+  let typeTypeId = findTypeTypeId();
+  let pointerSizeEnum = { One: 0, Many: 1, Slice: 2, C: 3 };
+
+  // for each package, is an array with packages to get to this one
+  let canonPkgPaths = computeCanonicalPackagePaths();
+
+  // for each decl, is an array with {declNames, pkgNames} to get to this one
+
+  let canonDeclPaths = null; // lazy; use getCanonDeclPath
+
+  // for each type, is an array with {declNames, pkgNames} to get to this one
+
+  let canonTypeDecls = null; // lazy; use getCanonTypeDecl
+
+  let curNav = {
+    showPrivDecls: false,
+    // each element is a package name, e.g. @import("a") then within there @import("b")
+    // starting implicitly from root package
+    pkgNames: [],
+    // same as above except actual packages, not names
+    pkgObjs: [],
+    // Each element is a decl name, `a.b.c`, a is 0, b is 1, c is 2, etc.
+    // empty array means refers to the package itself
+    declNames: [],
+    // these will be all types, except the last one may be a type or a decl
+    declObjs: [],
+
+    // (a, b, c, d) comptime call; result is the value the docs refer to
+    callName: null,
+  };
+
+  let curNavSearch = "";
+  let curSearchIndex = -1;
+  let imFeelingLucky = false;
+
+  let rootIsStd = detectRootIsStd();
+
+  // map of decl index to list of non-generic fn indexes
+  // let nodesToFnsMap = indexNodesToFns();
+  // map of decl index to list of comptime fn calls
+  // let nodesToCallsMap = indexNodesToCalls();
+
+  domSearch.addEventListener("keydown", onSearchKeyDown, false);
+  domPrivDeclsBox.addEventListener(
+    "change",
+    function () {
+      if (this.checked != curNav.showPrivDecls) {
+        if (
+          this.checked &&
+          location.hash.length > 1 &&
+          location.hash[1] != "*"
+        ) {
+          location.hash = "#*" + location.hash.substring(1);
+          return;
+        }
+        if (
+          !this.checked &&
+          location.hash.length > 1 &&
+          location.hash[1] == "*"
+        ) {
+          location.hash = "#" + location.hash.substring(2);
+          return;
+        }
+      }
+    },
+    false
+  );
+
+  if (location.hash == "") {
+    location.hash = "#root";
+  }
+
+  window.addEventListener("hashchange", onHashChange, false);
+  window.addEventListener("keydown", onWindowKeyDown, false);
+  onHashChange();
+
+  function renderTitle() {
+    let list = curNav.pkgNames.concat(curNav.declNames);
+    let suffix = " - Zig";
+    if (list.length === 0) {
+      if (rootIsStd) {
+        document.title = "std" + suffix;
+      } else {
+        document.title = zigAnalysis.params.rootName + suffix;
+      }
+    } else {
+      document.title = list.join(".") + suffix;
+    }
+  }
 
-    let rootIsStd = detectRootIsStd();
+  function isDecl(x) {
+    return "value" in x;
+  }
 
-    // map of decl index to list of non-generic fn indexes
-    // let nodesToFnsMap = indexNodesToFns();
-    // map of decl index to list of comptime fn calls
-    // let nodesToCallsMap = indexNodesToCalls();
+  function isType(x) {
+    return "kind" in x && !("value" in x);
+  }
 
-    domSearch.addEventListener('keydown', onSearchKeyDown, false);
-    domPrivDeclsBox.addEventListener('change', function() {
-        if (this.checked != curNav.showPrivDecls) {
-            if (this.checked && location.hash.length > 1 && location.hash[1] != '*'){
-                location.hash = "#*" + location.hash.substring(1);
-                return;
-            }
-            if (!this.checked && location.hash.length > 1 && location.hash[1] == '*') {
-                location.hash = "#" + location.hash.substring(2);
-                return;
-            }
-        }
-    }, false);
-    
-    if (location.hash == "") {
-        location.hash = "#root";
-    }
-    
-    window.addEventListener('hashchange', onHashChange, false);
-    window.addEventListener('keydown', onWindowKeyDown, false);
-    onHashChange();
-
-    function renderTitle() {
-        let list = curNav.pkgNames.concat(curNav.declNames);
-        let suffix = " - Zig";
-        if (list.length === 0) {
-            if (rootIsStd) {
-                document.title = "std" + suffix;
-            } else {
-                document.title = zigAnalysis.params.rootName + suffix;
-            }
-        } else {
-            document.title = list.join('.') + suffix;
-        }
-    }
+  function isContainerType(x) {
+    return isType(x) && typeKindIsContainer(x.kind);
+  }
 
-    
-    function isDecl(x) {
-        return "value" in x;
+  function typeShorthandName(expr) {
+    let resolvedExpr = resolveValue({ expr: expr });
+    if (!("type" in resolvedExpr)) {
+      return null;
     }
+    let type = zigAnalysis.types[resolvedExpr.type];
+
+    outer: for (let i = 0; i < 10000; i += 1) {
+      switch (type.kind) {
+        case typeKinds.Optional:
+        case typeKinds.Pointer:
+          let child = type.child;
+          let resolvedChild = resolveValue(child);
+          if ("type" in resolvedChild) {
+            type = zigAnalysis.types[resolvedChild.type];
+            continue;
+          } else {
+            return null;
+          }
+        default:
+          break outer;
+      }
 
-    
-    function isType(x) {
-        return "kind" in x && !("value" in x);
+      if (i == 9999) throw "Exhausted typeShorthandName quota";
     }
 
-    
-    function isContainerType(x) {
-        return isType(x) && typeKindIsContainer((x).kind) ;
+    let name = undefined;
+    if (type.kind === typeKinds.Struct) {
+      name = "struct";
+    } else if (type.kind === typeKinds.Enum) {
+      name = "enum";
+    } else if (type.kind === typeKinds.Union) {
+      name = "union";
+    } else {
+      console.log("TODO: unhalndled case in typeShortName");
+      return null;
     }
 
-    
-    function typeShorthandName(expr) {
-        let resolvedExpr = resolveValue({expr: expr});
-        if (!("type" in resolvedExpr)) {
-            return null;
-        }
-        let type = (zigAnalysis.types[resolvedExpr.type]);
-
-        outer: for (let i = 0; i < 10000; i += 1) {
-            switch (type.kind) {
-                case typeKinds.Optional:
-                case typeKinds.Pointer:
-                    let child = (type).child;
-                    let resolvedChild = resolveValue(child);
-                    if ("type" in resolvedChild) {
-                        type = zigAnalysis.types[resolvedChild.type];
-                        continue;
-                    } else {
-                        return null;
-                    }
-                default:
-                    break outer;
-            }
-
-            if (i == 9999) throw "Exhausted typeShorthandName quota";
-        }
-
+    return escapeHtml(name);
+  }
+
+  function typeKindIsContainer(typeKind) {
+    return (
+      typeKind === typeKinds.Struct ||
+      typeKind === typeKinds.Union ||
+      typeKind === typeKinds.Enum
+    );
+  }
+
+  function declCanRepresentTypeKind(typeKind) {
+    return typeKind === typeKinds.ErrorSet || typeKindIsContainer(typeKind);
+  }
+
+  //
+  // function findCteInRefPath(path) {
+  //     for (let i = path.length - 1; i >= 0; i -= 1) {
+  //         const ref = path[i];
+  //         if ("string" in ref) continue;
+  //         if ("comptimeExpr" in ref) return ref;
+  //         if ("refPath" in ref) return findCteInRefPath(ref.refPath);
+  //         return null;
+  //     }
+
+  //     return null;
+  // }
+
+  function resolveValue(value) {
+    let i = 0;
+    while (i < 1000) {
+      i += 1;
+
+      if ("refPath" in value.expr) {
+        value = { expr: value.expr.refPath[value.expr.refPath.length - 1] };
+        continue;
+      }
 
+      if ("declRef" in value.expr) {
+        value = zigAnalysis.decls[value.expr.declRef].value;
+        continue;
+      }
 
-        let name = undefined;
-        if (type.kind === typeKinds.Struct) {
-            name = "struct";
-        } else if (type.kind === typeKinds.Enum) {
-            name = "enum";
-        } else if (type.kind === typeKinds.Union) {
-            name = "union";
-        } else {
-            console.log("TODO: unhalndled case in typeShortName");
-            return null;
-        }
+      if ("as" in value.expr) {
+        value = {
+          typeRef: zigAnalysis.exprs[value.expr.as.typeRefArg],
+          expr: zigAnalysis.exprs[value.expr.as.exprArg],
+        };
+        continue;
+      }
 
-        return escapeHtml(name);
+      return value;
     }
-
-    
-    function typeKindIsContainer(typeKind) {
-        return typeKind === typeKinds.Struct ||
-            typeKind === typeKinds.Union ||
-            typeKind === typeKinds.Enum;
+    console.assert(false);
+    return {};
+  }
+
+  //    function typeOfDecl(decl){
+  //        return decl.value.typeRef;
+  //
+  //        let i = 0;
+  //        while(i < 1000) {
+  //            i += 1;
+  //            console.assert(isDecl(decl));
+  //            if ("type" in decl.value) {
+  //                return ({ type: typeTypeId });
+  //            }
+  //
+  ////            if ("string" in decl.value) {
+  ////                return ({ type: {
+  ////                  kind: typeKinds.Pointer,
+  ////                  size: pointerSizeEnum.One,
+  ////                  child: });
+  ////            }
+  //
+  //            if ("refPath" in decl.value) {
+  //                decl =  ({
+  //                  value: decl.value.refPath[decl.value.refPath.length -1]
+  //                });
+  //                continue;
+  //            }
+  //
+  //            if ("declRef" in decl.value) {
+  //                decl = zigAnalysis.decls[decl.value.declRef];
+  //                continue;
+  //            }
+  //
+  //            if ("int" in decl.value) {
+  //                return decl.value.int.typeRef;
+  //            }
+  //
+  //            if ("float" in decl.value) {
+  //                return decl.value.float.typeRef;
+  //            }
+  //
+  //            if ("array" in decl.value) {
+  //                return decl.value.array.typeRef;
+  //            }
+  //
+  //            if ("struct" in decl.value) {
+  //                return decl.value.struct.typeRef;
+  //            }
+  //
+  //            if ("comptimeExpr" in decl.value) {
+  //                const cte = zigAnalysis.comptimeExprs[decl.value.comptimeExpr];
+  //                return cte.typeRef;
+  //            }
+  //
+  //            if ("call" in decl.value) {
+  //                const fn_call = zigAnalysis.calls[decl.value.call];
+  //                let fn_decl = undefined;
+  //                if ("declRef" in fn_call.func) {
+  //                    fn_decl = zigAnalysis.decls[fn_call.func.declRef];
+  //                } else if ("refPath" in fn_call.func) {
+  //                    console.assert("declRef" in fn_call.func.refPath[fn_call.func.refPath.length -1]);
+  //                    fn_decl = zigAnalysis.decls[fn_call.func.refPath[fn_call.func.refPath.length -1].declRef];
+  //                } else throw {};
+  //
+  //                const fn_decl_value = resolveValue(fn_decl.value);
+  //                console.assert("type" in fn_decl_value); //TODO handle comptimeExpr
+  //                const fn_type = (zigAnalysis.types[fn_decl_value.type]);
+  //                console.assert(fn_type.kind === typeKinds.Fn);
+  //                return fn_type.ret;
+  //            }
+  //
+  //            if ("void" in decl.value) {
+  //                return ({ type: typeTypeId });
+  //            }
+  //
+  //            if ("bool" in decl.value) {
+  //                return ({ type: typeKinds.Bool });
+  //            }
+  //
+  //            console.log("TODO: handle in `typeOfDecl` more cases: ", decl);
+  //            console.assert(false);
+  //            throw {};
+  //        }
+  //        console.assert(false);
+  //        return ({});
+  //    }
+
+  function render() {
+    domStatus.classList.add("hidden");
+    domFnProto.classList.add("hidden");
+    domSectParams.classList.add("hidden");
+    domTldDocs.classList.add("hidden");
+    domSectMainPkg.classList.add("hidden");
+    domSectPkgs.classList.add("hidden");
+    domSectTypes.classList.add("hidden");
+    domSectTests.classList.add("hidden");
+    domSectNamespaces.classList.add("hidden");
+    domSectErrSets.classList.add("hidden");
+    domSectFns.classList.add("hidden");
+    domSectFields.classList.add("hidden");
+    domSectSearchResults.classList.add("hidden");
+    domSectSearchNoResults.classList.add("hidden");
+    domSectInfo.classList.add("hidden");
+    domHdrName.classList.add("hidden");
+    domSectNav.classList.add("hidden");
+    domSectFnErrors.classList.add("hidden");
+    domFnExamples.classList.add("hidden");
+    domFnNoExamples.classList.add("hidden");
+    domDeclNoRef.classList.add("hidden");
+    domFnErrorsAnyError.classList.add("hidden");
+    domTableFnErrors.classList.add("hidden");
+    domSectGlobalVars.classList.add("hidden");
+    domSectValues.classList.add("hidden");
+
+    renderTitle();
+    renderInfo();
+    renderPkgList();
+
+    domPrivDeclsBox.checked = curNav.showPrivDecls;
+
+    if (curNavSearch !== "") {
+      return renderSearch();
     }
 
-    
-    function declCanRepresentTypeKind(typeKind) {
-        return typeKind === typeKinds.ErrorSet || typeKindIsContainer(typeKind);
+    let rootPkg = zigAnalysis.packages[zigAnalysis.rootPkg];
+    let pkg = rootPkg;
+    curNav.pkgObjs = [pkg];
+    for (let i = 0; i < curNav.pkgNames.length; i += 1) {
+      let childPkg = zigAnalysis.packages[pkg.table[curNav.pkgNames[i]]];
+      if (childPkg == null) {
+        return render404();
+      }
+      pkg = childPkg;
+      curNav.pkgObjs.push(pkg);
     }
 
-    // 
-    // function findCteInRefPath(path) {
-    //     for (let i = path.length - 1; i >= 0; i -= 1) {
-    //         const ref = path[i];
-    //         if ("string" in ref) continue;
-    //         if ("comptimeExpr" in ref) return ref;
-    //         if ("refPath" in ref) return findCteInRefPath(ref.refPath);
-    //         return null;
-    //     }
-
-    //     return null;
-    // }
-
-    
-    function resolveValue(value) {
-        let i = 0;
-        while(i < 1000) {
-            i += 1;
-
-            if ("refPath" in value.expr) {
-                value = {expr: value.expr.refPath[value.expr.refPath.length -1]};
-                continue;
-            }
-
-            if ("declRef" in value.expr) {
-                value = zigAnalysis.decls[value.expr.declRef].value;
-                continue;
-            }
-
-            if ("as" in value.expr) {
-                value = {
-                  typeRef: zigAnalysis.exprs[value.expr.as.typeRefArg],
-                  expr: zigAnalysis.exprs[value.expr.as.exprArg],
-                };
-                continue;
-            }
-
-            return value;
-
-        }
-        console.assert(false);
-        return ({});
-    }
-
-    
-//    function typeOfDecl(decl){
-//        return decl.value.typeRef;
-//
-//        let i = 0;
-//        while(i < 1000) {
-//            i += 1;
-//            console.assert(isDecl(decl));
-//            if ("type" in decl.value) {
-//                return ({ type: typeTypeId });
-//            }
-//
-////            if ("string" in decl.value) {
-////                return ({ type: {
-////                  kind: typeKinds.Pointer,
-////                  size: pointerSizeEnum.One,
-////                  child: });
-////            }
-//
-//            if ("refPath" in decl.value) {
-//                decl =  ({
-//                  value: decl.value.refPath[decl.value.refPath.length -1]
-//                });
-//                continue;
-//            }
-//
-//            if ("declRef" in decl.value) {
-//                decl = zigAnalysis.decls[decl.value.declRef];
-//                continue;
-//            }
-//
-//            if ("int" in decl.value) {
-//                return decl.value.int.typeRef;
-//            }
-//
-//            if ("float" in decl.value) {
-//                return decl.value.float.typeRef;
-//            }
-//
-//            if ("array" in decl.value) {
-//                return decl.value.array.typeRef;
-//            }
-//
-//            if ("struct" in decl.value) {
-//                return decl.value.struct.typeRef;
-//            }
-//
-//            if ("comptimeExpr" in decl.value) {
-//                const cte = zigAnalysis.comptimeExprs[decl.value.comptimeExpr];
-//                return cte.typeRef;
-//            }
-//
-//            if ("call" in decl.value) {
-//                const fn_call = zigAnalysis.calls[decl.value.call];
-//                let fn_decl = undefined;
-//                if ("declRef" in fn_call.func) {
-//                    fn_decl = zigAnalysis.decls[fn_call.func.declRef];
-//                } else if ("refPath" in fn_call.func) {
-//                    console.assert("declRef" in fn_call.func.refPath[fn_call.func.refPath.length -1]);
-//                    fn_decl = zigAnalysis.decls[fn_call.func.refPath[fn_call.func.refPath.length -1].declRef];
-//                } else throw {};
-//
-//                const fn_decl_value = resolveValue(fn_decl.value);
-//                console.assert("type" in fn_decl_value); //TODO handle comptimeExpr
-//                const fn_type = (zigAnalysis.types[fn_decl_value.type]);
-//                console.assert(fn_type.kind === typeKinds.Fn);
-//                return fn_type.ret;
-//            }
-//
-//            if ("void" in decl.value) {
-//                return ({ type: typeTypeId });
-//            }
-//
-//            if ("bool" in decl.value) {
-//                return ({ type: typeKinds.Bool });
-//            }
-//
-//            console.log("TODO: handle in `typeOfDecl` more cases: ", decl);
-//            console.assert(false);
-//            throw {};
-//        }
-//        console.assert(false);
-//        return ({});
-//    }
-
-    function render() {
-        domStatus.classList.add("hidden");
-        domFnProto.classList.add("hidden");
-        domSectParams.classList.add("hidden");
-        domTldDocs.classList.add("hidden");
-        domSectMainPkg.classList.add("hidden");
-        domSectPkgs.classList.add("hidden");
-        domSectTypes.classList.add("hidden");
-        domSectTests.classList.add("hidden");
-        domSectNamespaces.classList.add("hidden");
-        domSectErrSets.classList.add("hidden");
-        domSectFns.classList.add("hidden");
-        domSectFields.classList.add("hidden");
-        domSectSearchResults.classList.add("hidden");
-        domSectSearchNoResults.classList.add("hidden");
-        domSectInfo.classList.add("hidden");
-        domHdrName.classList.add("hidden");
-        domSectNav.classList.add("hidden");
-        domSectFnErrors.classList.add("hidden");
-        domFnExamples.classList.add("hidden");
-        domFnNoExamples.classList.add("hidden");
-        domDeclNoRef.classList.add("hidden");
-        domFnErrorsAnyError.classList.add("hidden");
-        domTableFnErrors.classList.add("hidden");
-        domSectGlobalVars.classList.add("hidden");
-        domSectValues.classList.add("hidden");
-
-        renderTitle();
-        renderInfo();
-        renderPkgList();
-
-        domPrivDeclsBox.checked = curNav.showPrivDecls;
-
-        if (curNavSearch !== "") {
-            return renderSearch();
-        }
-
-        let rootPkg = zigAnalysis.packages[zigAnalysis.rootPkg];
-        let pkg = rootPkg;
-        curNav.pkgObjs = [pkg];
-        for (let i = 0; i < curNav.pkgNames.length; i += 1) {
-            let childPkg = zigAnalysis.packages[pkg.table[curNav.pkgNames[i]]];
-            if (childPkg == null) {
-                return render404();
-            }
-            pkg = childPkg;
-            curNav.pkgObjs.push(pkg);
-        }
-
-        
-        let currentType = zigAnalysis.types[pkg.main];
-        curNav.declObjs = [currentType];
-        for (let i = 0; i < curNav.declNames.length; i += 1) {
-
-            
-            let childDecl = findSubDecl((currentType), curNav.declNames[i]);
-            if (childDecl == null) {
-                return render404();
-            }
-
-            let childDeclValue = resolveValue((childDecl).value).expr;
-            if ("type" in childDeclValue) {
-
-                const t = zigAnalysis.types[childDeclValue.type];
-                if (t.kind != typeKinds.Fn) {
-                    childDecl = t;
-                }
-            }
-
-            currentType = (childDecl);
-            curNav.declObjs.push(currentType);
-        }
-
-        renderNav();
-
-        let last = curNav.declObjs[curNav.declObjs.length - 1];
-        let lastIsDecl = isDecl(last);
-        let lastIsType = isType(last);
-        let lastIsContainerType = isContainerType(last);
-
-        if (lastIsContainerType) {
-            return renderContainer((last));
-        }
-
-        if (!lastIsDecl && !lastIsType) {
-            return renderUnknownDecl((last));
-        }
-
-        if (lastIsType) {
-            return renderType((last));
-        }
+    let currentType = zigAnalysis.types[pkg.main];
+    curNav.declObjs = [currentType];
+    for (let i = 0; i < curNav.declNames.length; i += 1) {
+      let childDecl = findSubDecl(currentType, curNav.declNames[i]);
+      if (childDecl == null) {
+        return render404();
+      }
 
-        if (lastIsDecl && last.kind === 'var') {
-            return renderVar((last));
+      let childDeclValue = resolveValue(childDecl.value).expr;
+      if ("type" in childDeclValue) {
+        const t = zigAnalysis.types[childDeclValue.type];
+        if (t.kind != typeKinds.Fn) {
+          childDecl = t;
         }
+      }
 
-        if (lastIsDecl && last.kind === 'const') {
-            let typeObj = zigAnalysis.types[resolveValue((last).value).expr.type];
-            if (typeObj && typeObj.kind === typeKinds.Fn) {
-                return renderFn((last));
-            }
-
-            return renderValue((last));
-        }
+      currentType = childDecl;
+      curNav.declObjs.push(currentType);
     }
 
-    
-    function renderUnknownDecl(decl) {
-        domDeclNoRef.classList.remove("hidden");
+    renderNav();
 
-        let docs = zigAnalysis.astNodes[decl.src].docs;
-        if (docs != null) {
-            domTldDocs.innerHTML = markdown(docs);
-        } else {
-            domTldDocs.innerHTML = '<p>There are no doc comments for this declaration.</p>';
-        }
-        domTldDocs.classList.remove("hidden");
-    }
+    let last = curNav.declObjs[curNav.declObjs.length - 1];
+    let lastIsDecl = isDecl(last);
+    let lastIsType = isType(last);
+    let lastIsContainerType = isContainerType(last);
 
-    
-    function typeIsErrSet(typeIndex) {
-        let typeObj = zigAnalysis.types[typeIndex];
-        return typeObj.kind === typeKinds.ErrorSet;
+    if (lastIsContainerType) {
+      return renderContainer(last);
     }
 
-    
-    function typeIsStructWithNoFields(typeIndex) {
-        let typeObj = zigAnalysis.types[typeIndex];
-        if (typeObj.kind !== typeKinds.Struct)
-            return false;
-        return (typeObj).fields.length == 0;
+    if (!lastIsDecl && !lastIsType) {
+      return renderUnknownDecl(last);
     }
 
-    
-    function typeIsGenericFn(typeIndex) {
-        let typeObj = zigAnalysis.types[typeIndex];
-        if (typeObj.kind !== typeKinds.Fn) {
-            return false;
-        }
-        return  (typeObj).generic_ret != null;
+    if (lastIsType) {
+      return renderType(last);
     }
 
-    
-    function renderFn(fnDecl) {
-        if ("refPath" in fnDecl.value.expr) {
-            let last = fnDecl.value.expr.refPath.length - 1;
-            let lastExpr = fnDecl.value.expr.refPath[last];
-            console.assert("declRef" in lastExpr);
-            fnDecl = zigAnalysis.decls[lastExpr.declRef];
-        }
-
-        let value = resolveValue(fnDecl.value);
-        console.assert("type" in value.expr);
-        let typeObj = (zigAnalysis.types[value.expr.type]);
-
-        domFnProtoCode.innerHTML = exprName(value.expr, {
-          wantHtml: true,
-          wantLink: true,
-          fnDecl,
-        });
-
-        let docsSource = null;
-        let srcNode = zigAnalysis.astNodes[fnDecl.src];
-        if (srcNode.docs != null) {
-            docsSource = srcNode.docs;
-        }
-
-        renderFnParamDocs(fnDecl, typeObj);
-
-        let retExpr = resolveValue({expr:typeObj.ret}).expr;
-        if ("type" in retExpr) {
-            let retIndex = retExpr.type;
-            let errSetTypeIndex = (null);
-            let retType = zigAnalysis.types[retIndex];
-            if (retType.kind === typeKinds.ErrorSet) {
-                errSetTypeIndex = retIndex;
-            } else if (retType.kind === typeKinds.ErrorUnion) {
-                errSetTypeIndex = (retType).err.type;
-            }
-            if (errSetTypeIndex != null) {
-                let errSetType = (zigAnalysis.types[errSetTypeIndex]);
-                renderErrorSet(errSetType);
-            }
-        }
-
-        let protoSrcIndex = fnDecl.src;
-        if (typeIsGenericFn(value.expr.type)) {
-            // does the generic_ret contain a container?
-            var resolvedGenericRet = resolveValue({expr: typeObj.generic_ret});
-            
-            if ("call" in resolvedGenericRet.expr){
-                let call  = zigAnalysis.calls[resolvedGenericRet.expr.call];
-                let resolvedFunc = resolveValue({expr: call.func});
-                if (!("type" in resolvedFunc.expr)) return;
-                let callee = zigAnalysis.types[resolvedFunc.expr.type];
-                if (!callee.generic_ret) return;
-                resolvedGenericRet = resolveValue({expr: callee.generic_ret});
-            }
+    if (lastIsDecl && last.kind === "var") {
+      return renderVar(last);
+    }
 
-            // TODO: see if unwrapping the `as` here is a good idea or not.
-            if ("as" in resolvedGenericRet.expr) {
-                resolvedGenericRet = {
-                    expr: zigAnalysis.exprs[resolvedGenericRet.expr.as.exprArg]
-                };
-            }
+    if (lastIsDecl && last.kind === "const") {
+      let typeObj = zigAnalysis.types[resolveValue(last.value).expr.type];
+      if (typeObj && typeObj.kind === typeKinds.Fn) {
+        return renderFn(last);
+      }
 
-            if (!("type" in resolvedGenericRet.expr)) return;
-            const genericType = zigAnalysis.types[resolvedGenericRet.expr.type];
-            if (isContainerType(genericType)) {
-                renderContainer(genericType)
-            }
+      return renderValue(last);
+    }
+  }
 
+  function renderUnknownDecl(decl) {
+    domDeclNoRef.classList.remove("hidden");
 
+    let docs = zigAnalysis.astNodes[decl.src].docs;
+    if (docs != null) {
+      domTldDocs.innerHTML = markdown(docs);
+    } else {
+      domTldDocs.innerHTML =
+        "<p>There are no doc comments for this declaration.</p>";
+    }
+    domTldDocs.classList.remove("hidden");
+  }
+
+  function typeIsErrSet(typeIndex) {
+    let typeObj = zigAnalysis.types[typeIndex];
+    return typeObj.kind === typeKinds.ErrorSet;
+  }
+
+  function typeIsStructWithNoFields(typeIndex) {
+    let typeObj = zigAnalysis.types[typeIndex];
+    if (typeObj.kind !== typeKinds.Struct) return false;
+    return typeObj.fields.length == 0;
+  }
+
+  function typeIsGenericFn(typeIndex) {
+    let typeObj = zigAnalysis.types[typeIndex];
+    if (typeObj.kind !== typeKinds.Fn) {
+      return false;
+    }
+    return typeObj.generic_ret != null;
+  }
+
+  function renderFn(fnDecl) {
+    if ("refPath" in fnDecl.value.expr) {
+      let last = fnDecl.value.expr.refPath.length - 1;
+      let lastExpr = fnDecl.value.expr.refPath[last];
+      console.assert("declRef" in lastExpr);
+      fnDecl = zigAnalysis.decls[lastExpr.declRef];
+    }
 
+    let value = resolveValue(fnDecl.value);
+    console.assert("type" in value.expr);
+    let typeObj = zigAnalysis.types[value.expr.type];
 
+    domFnProtoCode.innerHTML = exprName(value.expr, {
+      wantHtml: true,
+      wantLink: true,
+      fnDecl,
+    });
 
-            // old code
-            // let instantiations = nodesToFnsMap[protoSrcIndex];
-            // let calls = nodesToCallsMap[protoSrcIndex];
-            // if (instantiations == null && calls == null) {
-            //     domFnNoExamples.classList.remove("hidden");
-            // } else if (calls != null) {
-            //     // if (fnObj.combined === undefined) fnObj.combined = allCompTimeFnCallsResult(calls);
-            //     if (fnObj.combined != null) renderContainer(fnObj.combined);
+    let docsSource = null;
+    let srcNode = zigAnalysis.astNodes[fnDecl.src];
+    if (srcNode.docs != null) {
+      docsSource = srcNode.docs;
+    }
 
-            //     resizeDomList(domListFnExamples, calls.length, '<li></li>');
+    renderFnParamDocs(fnDecl, typeObj);
+
+    let retExpr = resolveValue({ expr: typeObj.ret }).expr;
+    if ("type" in retExpr) {
+      let retIndex = retExpr.type;
+      let errSetTypeIndex = null;
+      let retType = zigAnalysis.types[retIndex];
+      if (retType.kind === typeKinds.ErrorSet) {
+        errSetTypeIndex = retIndex;
+      } else if (retType.kind === typeKinds.ErrorUnion) {
+        errSetTypeIndex = retType.err.type;
+      }
+      if (errSetTypeIndex != null) {
+        let errSetType = zigAnalysis.types[errSetTypeIndex];
+        renderErrorSet(errSetType);
+      }
+    }
 
-            //     for (let callI = 0; callI < calls.length; callI += 1) {
-            //         let liDom = domListFnExamples.children[callI];
-            //         liDom.innerHTML = getCallHtml(fnDecl, calls[callI]);
-            //     }
+    let protoSrcIndex = fnDecl.src;
+    if (typeIsGenericFn(value.expr.type)) {
+      // does the generic_ret contain a container?
+      var resolvedGenericRet = resolveValue({ expr: typeObj.generic_ret });
+
+      if ("call" in resolvedGenericRet.expr) {
+        let call = zigAnalysis.calls[resolvedGenericRet.expr.call];
+        let resolvedFunc = resolveValue({ expr: call.func });
+        if (!("type" in resolvedFunc.expr)) return;
+        let callee = zigAnalysis.types[resolvedFunc.expr.type];
+        if (!callee.generic_ret) return;
+        resolvedGenericRet = resolveValue({ expr: callee.generic_ret });
+      }
 
-            //     domFnExamples.classList.remove("hidden");
-            // } else if (instantiations != null) {
-            //     // TODO
-            // }
-        } else {
+      // TODO: see if unwrapping the `as` here is a good idea or not.
+      if ("as" in resolvedGenericRet.expr) {
+        resolvedGenericRet = {
+          expr: zigAnalysis.exprs[resolvedGenericRet.expr.as.exprArg],
+        };
+      }
 
-            domFnExamples.classList.add("hidden");
-            domFnNoExamples.classList.add("hidden");
-        }
+      if (!("type" in resolvedGenericRet.expr)) return;
+      const genericType = zigAnalysis.types[resolvedGenericRet.expr.type];
+      if (isContainerType(genericType)) {
+        renderContainer(genericType);
+      }
 
-        let protoSrcNode = zigAnalysis.astNodes[protoSrcIndex];
-        if (docsSource == null && protoSrcNode != null && protoSrcNode.docs != null) {
-            docsSource = protoSrcNode.docs;
-        }
-        if (docsSource != null) {
-            domTldDocs.innerHTML = markdown(docsSource);
-            domTldDocs.classList.remove("hidden");
-        }
-        domFnProto.classList.remove("hidden");
+      // old code
+      // let instantiations = nodesToFnsMap[protoSrcIndex];
+      // let calls = nodesToCallsMap[protoSrcIndex];
+      // if (instantiations == null && calls == null) {
+      //     domFnNoExamples.classList.remove("hidden");
+      // } else if (calls != null) {
+      //     // if (fnObj.combined === undefined) fnObj.combined = allCompTimeFnCallsResult(calls);
+      //     if (fnObj.combined != null) renderContainer(fnObj.combined);
+
+      //     resizeDomList(domListFnExamples, calls.length, '<li></li>');
+
+      //     for (let callI = 0; callI < calls.length; callI += 1) {
+      //         let liDom = domListFnExamples.children[callI];
+      //         liDom.innerHTML = getCallHtml(fnDecl, calls[callI]);
+      //     }
+
+      //     domFnExamples.classList.remove("hidden");
+      // } else if (instantiations != null) {
+      //     // TODO
+      // }
+    } else {
+      domFnExamples.classList.add("hidden");
+      domFnNoExamples.classList.add("hidden");
     }
 
-    
-    function renderFnParamDocs(fnDecl, typeObj) {
-        let docCount = 0;
-
-        let fnNode = zigAnalysis.astNodes[fnDecl.src];
-        let fields = (fnNode.fields);
-        let isVarArgs = fnNode.varArgs;
-
-        for (let i = 0; i < fields.length; i += 1) {
-            let field = fields[i];
-            let fieldNode = zigAnalysis.astNodes[field];
-            if (fieldNode.docs != null) {
-                docCount += 1;
-            }
-        }
-        if (docCount == 0) {
-            return;
-        }
-
-        resizeDomList(domListParams, docCount, '<div></div>');
-        let domIndex = 0;
+    let protoSrcNode = zigAnalysis.astNodes[protoSrcIndex];
+    if (
+      docsSource == null &&
+      protoSrcNode != null &&
+      protoSrcNode.docs != null
+    ) {
+      docsSource = protoSrcNode.docs;
+    }
+    if (docsSource != null) {
+      domTldDocs.innerHTML = markdown(docsSource);
+      domTldDocs.classList.remove("hidden");
+    }
+    domFnProto.classList.remove("hidden");
+  }
 
-        for (let i = 0; i < fields.length; i += 1) {
-            let field = fields[i];
-            let fieldNode = zigAnalysis.astNodes[field];
-            let docs = fieldNode.docs;
-            if (fieldNode.docs == null) {
-                continue;
-            }
-            let docsNonEmpty = docs !== "";
-            let divDom = domListParams.children[domIndex];
-            domIndex += 1;
+  function renderFnParamDocs(fnDecl, typeObj) {
+    let docCount = 0;
 
+    let fnNode = zigAnalysis.astNodes[fnDecl.src];
+    let fields = fnNode.fields;
+    let isVarArgs = fnNode.varArgs;
 
-            let value = typeObj.params[i];
-            let preClass = docsNonEmpty ? ' class="fieldHasDocs"' : "";
-            let html = '<pre' + preClass + '>' + escapeHtml((fieldNode.name)) + ": ";
-            if (isVarArgs && i === typeObj.params.length - 1) {
-                html += '...';
-            } else {
-                let name = exprName(value, {wantHtml: false, wantLink: false});
-                html += '<span class="tok-kw">' + name + '</span>';
-            }
+    for (let i = 0; i < fields.length; i += 1) {
+      let field = fields[i];
+      let fieldNode = zigAnalysis.astNodes[field];
+      if (fieldNode.docs != null) {
+        docCount += 1;
+      }
+    }
+    if (docCount == 0) {
+      return;
+    }
 
-            html += ',</pre>';
+    resizeDomList(domListParams, docCount, "<div></div>");
+    let domIndex = 0;
 
-            if (docsNonEmpty) {
-                html += '<div class="fieldDocs">' + markdown(docs) + '</div>';
-            }
-            divDom.innerHTML = html;
-        }
-        domSectParams.classList.remove("hidden");
-    }
-
-    function renderNav() {
-        let len = curNav.pkgNames.length + curNav.declNames.length;
-        resizeDomList(domListNav, len, '<li><a href="#"></a></li>');
-        let list = [];
-        let hrefPkgNames = [];
-        let hrefDeclNames = ([]);
-        for (let i = 0; i < curNav.pkgNames.length; i += 1) {
-            hrefPkgNames.push(curNav.pkgNames[i]);
-            let name = curNav.pkgNames[i];
-            if (name == "root") name = zigAnalysis.rootPkgName;
-            list.push({
-                name: name,
-                link: navLink(hrefPkgNames, hrefDeclNames),
-            });
-        }
-        for (let i = 0; i < curNav.declNames.length; i += 1) {
-            hrefDeclNames.push(curNav.declNames[i]);
-            list.push({
-                name: curNav.declNames[i],
-                link: navLink(hrefPkgNames, hrefDeclNames),
-            });
-        }
+    for (let i = 0; i < fields.length; i += 1) {
+      let field = fields[i];
+      let fieldNode = zigAnalysis.astNodes[field];
+      let docs = fieldNode.docs;
+      if (fieldNode.docs == null) {
+        continue;
+      }
+      let docsNonEmpty = docs !== "";
+      let divDom = domListParams.children[domIndex];
+      domIndex += 1;
+
+      let value = typeObj.params[i];
+      let preClass = docsNonEmpty ? ' class="fieldHasDocs"' : "";
+      let html = "<pre" + preClass + ">" + escapeHtml(fieldNode.name) + ": ";
+      if (isVarArgs && i === typeObj.params.length - 1) {
+        html += "...";
+      } else {
+        let name = exprName(value, { wantHtml: false, wantLink: false });
+        html += '<span class="tok-kw">' + name + "</span>";
+      }
 
-        for (let i = 0; i < list.length; i += 1) {
-            let liDom = domListNav.children[i];
-            let aDom = liDom.children[0];
-            aDom.textContent = list[i].name;
-            aDom.setAttribute('href', list[i].link);
-            if (i + 1 == list.length) {
-                aDom.classList.add("active");
-            } else {
-                aDom.classList.remove("active");
-            }
-        }
+      html += ",</pre>";
 
-        domSectNav.classList.remove("hidden");
+      if (docsNonEmpty) {
+        html += '<div class="fieldDocs">' + markdown(docs) + "</div>";
+      }
+      divDom.innerHTML = html;
     }
-
-    function renderInfo() {
-        domTdZigVer.textContent = zigAnalysis.params.zigVersion;
-        //domTdTarget.textContent = zigAnalysis.params.builds[0].target;
-
-        domSectInfo.classList.remove("hidden");
+    domSectParams.classList.remove("hidden");
+  }
+
+  function renderNav() {
+    let len = curNav.pkgNames.length + curNav.declNames.length;
+    resizeDomList(domListNav, len, '<li><a href="#"></a></li>');
+    let list = [];
+    let hrefPkgNames = [];
+    let hrefDeclNames = [];
+    for (let i = 0; i < curNav.pkgNames.length; i += 1) {
+      hrefPkgNames.push(curNav.pkgNames[i]);
+      let name = curNav.pkgNames[i];
+      if (name == "root") name = zigAnalysis.rootPkgName;
+      list.push({
+        name: name,
+        link: navLink(hrefPkgNames, hrefDeclNames),
+      });
     }
-
-    function render404() {
-        domStatus.textContent = "404 Not Found";
-        domStatus.classList.remove("hidden");
+    for (let i = 0; i < curNav.declNames.length; i += 1) {
+      hrefDeclNames.push(curNav.declNames[i]);
+      list.push({
+        name: curNav.declNames[i],
+        link: navLink(hrefPkgNames, hrefDeclNames),
+      });
     }
 
-    function renderPkgList() {
-        let rootPkg = zigAnalysis.packages[zigAnalysis.rootPkg];
-        let list = [];
-        for (let key in rootPkg.table) {
-            let pkgIndex = rootPkg.table[key];
-            if (zigAnalysis.packages[pkgIndex] == null) continue;
-            if (key == zigAnalysis.params.rootName) continue;
-            list.push({
-                name: key,
-                pkg: pkgIndex,
-            });
-        }
-
-        {
-            let aDom = domSectMainPkg.children[1].children[0].children[0];
-            aDom.textContent = zigAnalysis.rootPkgName;
-            aDom.setAttribute('href', navLinkPkg(zigAnalysis.rootPkg));
-            if (zigAnalysis.params.rootName === curNav.pkgNames[0]) {
-                aDom.classList.add("active");
-            } else {
-                aDom.classList.remove("active");
-            }
-            domSectMainPkg.classList.remove("hidden");
-        }
-
-        list.sort(function(a, b) {
-            return operatorCompare(a.name.toLowerCase(), b.name.toLowerCase());
-        });
-
-        if (list.length !== 0) {
-            resizeDomList(domListPkgs, list.length, '<li><a href="#"></a></li>');
-            for (let i = 0; i < list.length; i += 1) {
-                let liDom = domListPkgs.children[i];
-                let aDom = liDom.children[0];
-                aDom.textContent = list[i].name;
-                aDom.setAttribute('href', navLinkPkg(list[i].pkg));
-                if (list[i].name === curNav.pkgNames[0]) {
-                    aDom.classList.add("active");
-                } else {
-                    aDom.classList.remove("active");
-                }
-            }
-
-            domSectPkgs.classList.remove("hidden");
-        }
+    for (let i = 0; i < list.length; i += 1) {
+      let liDom = domListNav.children[i];
+      let aDom = liDom.children[0];
+      aDom.textContent = list[i].name;
+      aDom.setAttribute("href", list[i].link);
+      if (i + 1 == list.length) {
+        aDom.classList.add("active");
+      } else {
+        aDom.classList.remove("active");
+      }
     }
 
-    
+    domSectNav.classList.remove("hidden");
+  }
+
+  function renderInfo() {
+    domTdZigVer.textContent = zigAnalysis.params.zigVersion;
+    //domTdTarget.textContent = zigAnalysis.params.builds[0].target;
+
+    domSectInfo.classList.remove("hidden");
+  }
+
+  function render404() {
+    domStatus.textContent = "404 Not Found";
+    domStatus.classList.remove("hidden");
+  }
+
+  function renderPkgList() {
+    let rootPkg = zigAnalysis.packages[zigAnalysis.rootPkg];
+    let list = [];
+    for (let key in rootPkg.table) {
+      let pkgIndex = rootPkg.table[key];
+      if (zigAnalysis.packages[pkgIndex] == null) continue;
+      if (key == zigAnalysis.params.rootName) continue;
+      list.push({
+        name: key,
+        pkg: pkgIndex,
+      });
+    }
 
-    function navLink(pkgNames, declNames, callName) {
-        let base = '#';
-        if (curNav.showPrivDecls) {
-            base += "*";
-        }
+    {
+      let aDom = domSectMainPkg.children[1].children[0].children[0];
+      aDom.textContent = zigAnalysis.rootPkgName;
+      aDom.setAttribute("href", navLinkPkg(zigAnalysis.rootPkg));
+      if (zigAnalysis.params.rootName === curNav.pkgNames[0]) {
+        aDom.classList.add("active");
+      } else {
+        aDom.classList.remove("active");
+      }
+      domSectMainPkg.classList.remove("hidden");
+    }
 
-        if (pkgNames.length === 0 && declNames.length === 0) {
-            return base;
-        } else if (declNames.length === 0 && callName == null) {
-            return base + pkgNames.join('.');
-        } else if (callName == null) {
-            return base + pkgNames.join('.') + ';' + declNames.join('.');
+    list.sort(function (a, b) {
+      return operatorCompare(a.name.toLowerCase(), b.name.toLowerCase());
+    });
+
+    if (list.length !== 0) {
+      resizeDomList(domListPkgs, list.length, '<li><a href="#"></a></li>');
+      for (let i = 0; i < list.length; i += 1) {
+        let liDom = domListPkgs.children[i];
+        let aDom = liDom.children[0];
+        aDom.textContent = list[i].name;
+        aDom.setAttribute("href", navLinkPkg(list[i].pkg));
+        if (list[i].name === curNav.pkgNames[0]) {
+          aDom.classList.add("active");
         } else {
-            return base + pkgNames.join('.') + ';' + declNames.join('.') + ';' + callName;
+          aDom.classList.remove("active");
         }
-    }
+      }
 
-    
-    function navLinkPkg(pkgIndex) {
-        return navLink(canonPkgPaths[pkgIndex], []);
+      domSectPkgs.classList.remove("hidden");
     }
+  }
 
-    
-    function navLinkDecl(childName) {
-        return navLink(curNav.pkgNames, curNav.declNames.concat([childName]));
+  function navLink(pkgNames, declNames, callName) {
+    let base = "#";
+    if (curNav.showPrivDecls) {
+      base += "*";
     }
 
-   //  
-   //  function navLinkCall(callObj) {
-   //      let declNamesCopy = curNav.declNames.concat([]);
-   //      let callName = (declNamesCopy.pop());
-
-   //      callName += '(';
-   //          for (let arg_i = 0; arg_i < callObj.args.length; arg_i += 1) {
-   //              if (arg_i !== 0) callName += ',';
-   //              let argObj = callObj.args[arg_i];
-   //              callName += getValueText(argObj, argObj, false, false);
-   //          }
-   //          callName += ')';
-
-   //      declNamesCopy.push(callName);
-   //      return navLink(curNav.pkgNames, declNamesCopy);
-   //  }
+    if (pkgNames.length === 0 && declNames.length === 0) {
+      return base;
+    } else if (declNames.length === 0 && callName == null) {
+      return base + pkgNames.join(".");
+    } else if (callName == null) {
+      return base + pkgNames.join(".") + ";" + declNames.join(".");
+    } else {
+      return (
+        base + pkgNames.join(".") + ";" + declNames.join(".") + ";" + callName
+      );
+    }
+  }
+
+  function navLinkPkg(pkgIndex) {
+    return navLink(canonPkgPaths[pkgIndex], []);
+  }
+
+  function navLinkDecl(childName) {
+    return navLink(curNav.pkgNames, curNav.declNames.concat([childName]));
+  }
+
+  //
+  //  function navLinkCall(callObj) {
+  //      let declNamesCopy = curNav.declNames.concat([]);
+  //      let callName = (declNamesCopy.pop());
+
+  //      callName += '(';
+  //          for (let arg_i = 0; arg_i < callObj.args.length; arg_i += 1) {
+  //              if (arg_i !== 0) callName += ',';
+  //              let argObj = callObj.args[arg_i];
+  //              callName += getValueText(argObj, argObj, false, false);
+  //          }
+  //          callName += ')';
+
+  //      declNamesCopy.push(callName);
+  //      return navLink(curNav.pkgNames, declNamesCopy);
+  //  }
+
+  function resizeDomListDl(dlDom, desiredLen) {
+    // add the missing dom entries
+    for (let i = dlDom.childElementCount / 2; i < desiredLen; i += 1) {
+      dlDom.insertAdjacentHTML("beforeend", "<dt></dt><dd></dd>");
+    }
+    // remove extra dom entries
+    while (desiredLen < dlDom.childElementCount / 2) {
+      dlDom.removeChild(dlDom.lastChild);
+      dlDom.removeChild(dlDom.lastChild);
+    }
+  }
 
-    
-    function resizeDomListDl(dlDom, desiredLen) {
-        // add the missing dom entries
-        for (let i = dlDom.childElementCount / 2; i < desiredLen; i += 1) {
-            dlDom.insertAdjacentHTML('beforeend', '<dt></dt><dd></dd>');
-        }
-        // remove extra dom entries
-        while (desiredLen < dlDom.childElementCount / 2) {
-            dlDom.removeChild(dlDom.lastChild);
-            dlDom.removeChild(dlDom.lastChild);
-        }
+  function resizeDomList(listDom, desiredLen, templateHtml) {
+    // add the missing dom entries
+    for (let i = listDom.childElementCount; i < desiredLen; i += 1) {
+      listDom.insertAdjacentHTML("beforeend", templateHtml);
+    }
+    // remove extra dom entries
+    while (desiredLen < listDom.childElementCount) {
+      listDom.removeChild(listDom.lastChild);
     }
+  }
 
-    
-    function resizeDomList(listDom, desiredLen, templateHtml) {
-        // add the missing dom entries
-        for (let i = listDom.childElementCount; i < desiredLen; i += 1) {
-            listDom.insertAdjacentHTML('beforeend', templateHtml);
+  function walkResultTypeRef(wr) {
+    if (wr.typeRef) return wr.typeRef;
+    let resolved = resolveValue(wr);
+    if (wr === resolved) {
+      return { type: 0 };
+    }
+    return walkResultTypeRef(resolved);
+  }
+
+  function exprName(expr, opts) {
+    switch (Object.keys(expr)[0]) {
+      default:
+        throw "this expression is not implemented yet";
+      case "bool": {
+        if (expr.bool) {
+          return "true";
+        }
+        return "false";
+      }
+      case "&": {
+        return "&" + exprName(zigAnalysis.exprs[expr["&"]]);
+      }
+      case "compileError": {
+        let compileError = expr.compileError;
+        return compileError;
+      }
+      case "enumLiteral": {
+        let literal = expr.enumLiteral;
+        return "." + literal;
+      }
+      case "void": {
+        return "void";
+      }
+      case "slice": {
+        let payloadHtml = "";
+        const lhsExpr = zigAnalysis.exprs[expr.slice.lhs];
+        const startExpr = zigAnalysis.exprs[expr.slice.start];
+        let decl = exprName(lhsExpr);
+        let start = exprName(startExpr);
+        let end = "";
+        let sentinel = "";
+        if (expr.slice["end"]) {
+          const endExpr = zigAnalysis.exprs[expr.slice.end];
+          let end_ = exprName(endExpr);
+          end += end_;
+        }
+        if (expr.slice["sentinel"]) {
+          const sentinelExpr = zigAnalysis.exprs[expr.slice.sentinel];
+          let sentinel_ = exprName(sentinelExpr);
+          sentinel += " :" + sentinel_;
+        }
+        payloadHtml += decl + "[" + start + ".." + end + sentinel + "]";
+        return payloadHtml;
+      }
+      case "sliceIndex": {
+        const sliceIndex = zigAnalysis.exprs[expr.sliceIndex];
+        return exprName(sliceIndex, opts);
+      }
+      case "cmpxchg": {
+        const typeIndex = zigAnalysis.exprs[expr.cmpxchg.type];
+        const ptrIndex = zigAnalysis.exprs[expr.cmpxchg.ptr];
+        const expectedValueIndex =
+          zigAnalysis.exprs[expr.cmpxchg.expected_value];
+        const newValueIndex = zigAnalysis.exprs[expr.cmpxchg.new_value];
+        const successOrderIndex = zigAnalysis.exprs[expr.cmpxchg.success_order];
+        const failureOrderIndex = zigAnalysis.exprs[expr.cmpxchg.failure_order];
+
+        const type = exprName(typeIndex, opts);
+        const ptr = exprName(ptrIndex, opts);
+        const expectedValue = exprName(expectedValueIndex, opts);
+        const newValue = exprName(newValueIndex, opts);
+        const successOrder = exprName(successOrderIndex, opts);
+        const failureOrder = exprName(failureOrderIndex, opts);
+
+        let fnName = "@";
+
+        switch (expr.cmpxchg.name) {
+          case "cmpxchg_strong": {
+            fnName += "cmpxchgStrong";
+            break;
+          }
+          case "cmpxchg_weak": {
+            fnName += "cmpxchgWeak";
+            break;
+          }
+          default: {
+            console.log("There's only cmpxchg_strong and cmpxchg_weak");
+          }
         }
-        // remove extra dom entries
-        while (desiredLen < listDom.childElementCount) {
-            listDom.removeChild(listDom.lastChild);
+
+        return (
+          fnName +
+          "(" +
+          type +
+          ", " +
+          ptr +
+          ", " +
+          expectedValue +
+          ", " +
+          newValue +
+          ", " +
+          "." +
+          successOrder +
+          ", " +
+          "." +
+          failureOrder +
+          ")"
+        );
+      }
+      case "cmpxchgIndex": {
+        const cmpxchgIndex = zigAnalysis.exprs[expr.cmpxchgIndex];
+        return exprName(cmpxchgIndex, opts);
+      }
+      case "switchOp": {
+        let condExpr = zigAnalysis.exprs[expr.switchOp.cond_index];
+        let ast = zigAnalysis.astNodes[expr.switchOp.ast];
+        let file_name = expr.switchOp.file_name;
+        let outer_decl_index = expr.switchOp.outer_decl;
+        let outer_decl = zigAnalysis.types[outer_decl_index];
+        let line = 0;
+        // console.log(expr.switchOp)
+        // console.log(outer_decl)
+        while (outer_decl_index !== 0 && outer_decl.line_number > 0) {
+          line += outer_decl.line_number;
+          outer_decl_index = outer_decl.outer_decl;
+          outer_decl = zigAnalysis.types[outer_decl_index];
+          // console.log(outer_decl)
+        }
+        line += ast.line + 1;
+        let payloadHtml = "";
+        let cond = exprName(condExpr, opts);
+
+        payloadHtml +=
+          "</br>" +
+          "node_name: " +
+          ast.name +
+          "</br>" +
+          "file: " +
+          file_name +
+          "</br>" +
+          "line: " +
+          line +
+          "</br>";
+        payloadHtml +=
+          "switch(" +
+          cond +
+          ") {" +
+          '<a href="https://github.com/ziglang/zig/tree/master/lib/std/' +
+          file_name +
+          "#L" +
+          line +
+          '">' +
+          "..." +
+          "</a>}";
+        return payloadHtml;
+      }
+      case "switchIndex": {
+        const switchIndex = zigAnalysis.exprs[expr.switchIndex];
+        return exprName(switchIndex, opts);
+      }
+      case "refPath": {
+        let name = exprName(expr.refPath[0]);
+        for (let i = 1; i < expr.refPath.length; i++) {
+          let component = undefined;
+          if ("string" in expr.refPath[i]) {
+            component = expr.refPath[i].string;
+          } else {
+            component = exprName(expr.refPath[i]);
+          }
+          name += "." + component;
         }
-    }
-     
-    function walkResultTypeRef(wr) {
-      if (wr.typeRef) return wr.typeRef;
-      let resolved = resolveValue(wr);
-      if (wr === resolved) {
-        return {type: 0};
-      }
-      return walkResultTypeRef(resolved);
-    }
-     
-    function exprName(expr, opts) {
-        switch (Object.keys(expr)[0]) {
-          default: throw "this expression is not implemented yet";
-          case "bool": {
-            if (expr.bool) {
-                return "true";
-            }
-            return "false";
+        return name;
+      }
+      case "fieldRef": {
+        const enumObj = exprName({ type: expr.fieldRef.type }, opts);
+        const field =
+          zigAnalysis.astNodes[enumObj.ast].fields[expr.fieldRef.index];
+        const name = zigAnalysis.astNodes[field].name;
+        return name;
+      }
+      case "enumToInt": {
+        const enumToInt = zigAnalysis.exprs[expr.enumToInt];
+        return "@enumToInt(" + exprName(enumToInt, opts) + ")";
+      }
+      case "bitSizeOf": {
+        const bitSizeOf = zigAnalysis.exprs[expr.bitSizeOf];
+        return "@bitSizeOf(" + exprName(bitSizeOf, opts) + ")";
+      }
+      case "sizeOf": {
+        const sizeOf = zigAnalysis.exprs[expr.sizeOf];
+        return "@sizeOf(" + exprName(sizeOf, opts) + ")";
+      }
+      case "builtinIndex": {
+        const builtinIndex = zigAnalysis.exprs[expr.builtinIndex];
+        return exprName(builtinIndex, opts);
+      }
+      case "builtin": {
+        const param_expr = zigAnalysis.exprs[expr.builtin.param];
+        let param = exprName(param_expr, opts);
+
+        let payloadHtml = "@";
+        switch (expr.builtin.name) {
+          case "align_of": {
+            payloadHtml += "alignOf";
+            break;
           }
-          case "&": {
-            return "&" + exprName(zigAnalysis.exprs[expr["&"]]);
+          case "bool_to_int": {
+            payloadHtml += "boolToInt";
+            break;
           }
-          case "compileError": {
-            let compileError = expr.compileError;
-            return compileError;
+          case "embed_file": {
+            payloadHtml += "embedFile";
+            break;
           }
-          case "enumLiteral": {
-            let literal = expr.enumLiteral;
-            return "." + literal;
+          case "error_name": {
+            payloadHtml += "errorName";
+            break;
           }
-          case "void": {
-            return "void";
+          case "panic": {
+            payloadHtml += "panic";
+            break;
           }
-          case "slice":{
-            let payloadHtml = "";
-            const lhsExpr = zigAnalysis.exprs[expr.slice.lhs];
-            const startExpr = zigAnalysis.exprs[expr.slice.start];
-            let decl = exprName(lhsExpr);
-            let start = exprName(startExpr);
-            let end = "";
-            let sentinel = "";
-            if (expr.slice['end']) {
-              const endExpr = zigAnalysis.exprs[expr.slice.end];
-              let end_ = exprName(endExpr);
-              end += end_;
-            }
-            if (expr.slice['sentinel']) {
-              const sentinelExpr = zigAnalysis.exprs[expr.slice.sentinel];
-              let sentinel_ = exprName(sentinelExpr);
-              sentinel += " :" + sentinel_;
-            }
-            payloadHtml += decl + "["+ start + ".." + end + sentinel + "]";
-            return payloadHtml;
+          case "set_cold": {
+            payloadHtml += "setCold";
+            break;
           }
-          case "sliceIndex": {
-            const sliceIndex = zigAnalysis.exprs[expr.sliceIndex];
-            return exprName(sliceIndex, opts);
-          }
-          case "cmpxchg":{
-            const typeIndex = zigAnalysis.exprs[expr.cmpxchg.type];
-            const ptrIndex = zigAnalysis.exprs[expr.cmpxchg.ptr];
-            const expectedValueIndex = zigAnalysis.exprs[expr.cmpxchg.expected_value];
-            const newValueIndex = zigAnalysis.exprs[expr.cmpxchg.new_value];
-            const successOrderIndex = zigAnalysis.exprs[expr.cmpxchg.success_order];
-            const failureOrderIndex = zigAnalysis.exprs[expr.cmpxchg.failure_order];
-
-            const type = exprName(typeIndex, opts);
-            const ptr = exprName(ptrIndex, opts);
-            const expectedValue = exprName(expectedValueIndex, opts);
-            const newValue = exprName(newValueIndex, opts);
-            const successOrder = exprName(successOrderIndex, opts);
-            const failureOrder = exprName(failureOrderIndex, opts);
-
-            let fnName = "@";
-
-            switch (expr.cmpxchg.name) {
-              case "cmpxchg_strong": {
-                fnName += "cmpxchgStrong"
-                break;
-              }
-              case "cmpxchg_weak": {
-                fnName += "cmpxchgWeak"
-                break;
-              }
-              default: {
-                console.log("There's only cmpxchg_strong and cmpxchg_weak");
-              }
-            }
-            
-            return fnName + "(" + type + ", " + ptr + ", " + expectedValue + ", "+  newValue + ", "+"." +successOrder + ", "+ "." +failureOrder + ")";
-          }
-          case "cmpxchgIndex": {
-            const cmpxchgIndex = zigAnalysis.exprs[expr.cmpxchgIndex];
-            return exprName(cmpxchgIndex, opts);
-          }
-          case "switchOp":{
-            let condExpr = zigAnalysis.exprs[expr.switchOp.cond_index];
-            let ast = zigAnalysis.astNodes[expr.switchOp.ast];
-            let file_name = expr.switchOp.file_name;
-            let outer_decl_index = expr.switchOp.outer_decl;
-            let outer_decl = zigAnalysis.types[outer_decl_index];
-            let line = 0;
-            // console.log(expr.switchOp)
-            // console.log(outer_decl)
-            while (outer_decl_index !== 0 && outer_decl.line_number > 0) {
-              line += outer_decl.line_number;
-              outer_decl_index = outer_decl.outer_decl;
-              outer_decl = zigAnalysis.types[outer_decl_index];
-            // console.log(outer_decl)
-            }
-            line += ast.line + 1;
-            let payloadHtml = "";
-            let cond = exprName(condExpr, opts);
-
-            payloadHtml += "</br>" + "node_name: " + ast.name + "</br>" + "file: " + file_name + "</br>" + "line: " + line + "</br>";
-            payloadHtml += "switch(" + cond + ") {" + "<a href=\"https://github.com/ziglang/zig/tree/master/lib/std/" + file_name + "#L" + line + "\">" +"..." + "</a>}";
-            return payloadHtml;
+          case "set_runtime_safety": {
+            payloadHtml += "setRuntimeSafety";
+            break;
           }
-          case "switchIndex": {
-            const switchIndex = zigAnalysis.exprs[expr.switchIndex];
-            return exprName(switchIndex, opts);
+          case "sqrt": {
+            payloadHtml += "sqrt";
+            break;
           }
-          case "refPath" : {
-            let name = exprName(expr.refPath[0]);
-            for (let i = 1; i < expr.refPath.length; i++) {
-                let component = undefined;
-                if ("string" in expr.refPath[i]) {
-                    component = expr.refPath[i].string;
-                } else {
-                    component = exprName(expr.refPath[i]);
-                }
-                name += "." + component;
-            }
-            return name;
+          case "sin": {
+            payloadHtml += "sin";
+            break;
           }
-          case "fieldRef" : {
-            const enumObj = exprName({"type":expr.fieldRef.type} ,opts);
-            const field = zigAnalysis.astNodes[enumObj.ast].fields[expr.fieldRef.index];
-            const name = zigAnalysis.astNodes[field].name;
-            return name
+          case "cos": {
+            payloadHtml += "cos";
+            break;
           }
-          case "enumToInt" : {
-            const enumToInt = zigAnalysis.exprs[expr.enumToInt];
-            return "@enumToInt(" + exprName(enumToInt, opts) + ")";
+          case "tan": {
+            payloadHtml += "tan";
+            break;
           }
-          case "bitSizeOf" : {
-            const bitSizeOf = zigAnalysis.exprs[expr.bitSizeOf];
-            return "@bitSizeOf(" + exprName(bitSizeOf, opts) + ")";
+          case "exp": {
+            payloadHtml += "exp";
+            break;
           }
-          case "sizeOf" : {
-            const sizeOf = zigAnalysis.exprs[expr.sizeOf];
-            return "@sizeOf(" + exprName(sizeOf, opts) + ")";
+          case "exp2": {
+            payloadHtml += "exp2";
+            break;
           }
-          case "builtinIndex" : {
-            const builtinIndex = zigAnalysis.exprs[expr.builtinIndex];
-            return exprName(builtinIndex, opts);
+          case "log": {
+            payloadHtml += "log";
+            break;
           }
-          case "builtin": {
-            const param_expr = zigAnalysis.exprs[expr.builtin.param];
-            let param = exprName(param_expr, opts);
-
-
-            let payloadHtml = "@";
-            switch (expr.builtin.name) {
-              case "align_of": {
-                payloadHtml += "alignOf";
-                break;
-              }
-              case "bool_to_int": {
-                payloadHtml += "boolToInt";
-                break;
-              }
-              case "embed_file": {
-                payloadHtml += "embedFile";
-                break;
-              }
-              case "error_name": {
-                payloadHtml += "errorName";
-                break;
-              }
-              case "panic": {
-                payloadHtml += "panic";
-                break;
-              }
-              case "set_cold": {
-                payloadHtml += "setCold";
-                break;
-              }
-              case "set_runtime_safety": {
-                payloadHtml += "setRuntimeSafety";
-                break;
-              }
-              case "sqrt": {
-                payloadHtml += "sqrt";
-                break;
-              }
-              case "sin": {
-                payloadHtml += "sin";
-                break;
-              }
-              case "cos": {
-                payloadHtml += "cos";
-                break;
-              }
-              case "tan": {
-                payloadHtml += "tan";
-                break;
-              }
-              case "exp": {
-                payloadHtml += "exp";
-                break;
-              }
-              case "exp2": {
-                payloadHtml += "exp2";
-                break;
-              }
-              case "log": {
-                payloadHtml += "log";
-                break;
-              }
-              case "log2": {
-                payloadHtml += "log2";
-                break;
-              }
-              case "log10": {
-                payloadHtml += "log10";
-                break;
-              }
-              case "fabs": {
-                payloadHtml += "fabs";
-                break;
-              }
-              case "floor": {
-                payloadHtml += "floor";
-                break;
-              }
-              case "ceil": {
-                payloadHtml += "ceil";
-                break;
-              }
-              case "trunc": {
-                payloadHtml += "trunc";
-                break;
-              }
-              case "round": {
-                payloadHtml += "round";
-                break;
-              }
-              case "tag_name": {
-                payloadHtml += "tagName";
-                break;
-              }
-              case "reify": {
-                payloadHtml += "Type";
-                break;
-              }
-              case "type_name": {
-                payloadHtml += "typeName";
-                break;
-              }
-              case "frame_type": {
-                payloadHtml += "Frame";
-                break;
-              }
-              case "frame_size": {
-                payloadHtml += "frameSize";
-                break;
-              }
-              case "ptr_to_int": {
-                payloadHtml += "ptrToInt";
-                break;
-              }
-              case "error_to_int": {
-                payloadHtml += "errorToInt";
-                break;
-              }
-              case "int_to_error": {
-                payloadHtml += "intToError";
-                break;
-              }
-              case "maximum": {
-                payloadHtml += "maximum";
-                break;
-              }
-              case "minimum": {
-                payloadHtml += "minimum";
-                break;
-              }
-              case "bit_not": {
-                return "~" + param;
-              }
-              case "clz": {
-                return "@clz(T" + ", " + param + ")";
-              }
-              case "ctz": {
-                return "@ctz(T" + ", " + param + ")";
-              }
-              case "pop_count": {
-                return "@popCount(T" + ", " + param + ")";
-              }
-              case "byte_swap": {
-                return "@byteSwap(T" + ", " + param + ")";
-              }
-              case "bit_reverse": {
-                return "@bitReverse(T" + ", " + param + ")";
-              }
-              default: console.log("builtin function not handled yet or doesn't exist!");
-            };
-            return payloadHtml + "(" + param + ")";
-
+          case "log2": {
+            payloadHtml += "log2";
+            break;
           }
-          case "builtinBinIndex" : {
-            const builtinBinIndex = zigAnalysis.exprs[expr.builtinBinIndex];
-            return exprName(builtinBinIndex, opts);
+          case "log10": {
+            payloadHtml += "log10";
+            break;
           }
-          case "builtinBin": {
-            const lhsOp = zigAnalysis.exprs[expr.builtinBin.lhs];
-            const rhsOp = zigAnalysis.exprs[expr.builtinBin.rhs];
-            let lhs = exprName(lhsOp, opts);
-            let rhs = exprName(rhsOp, opts);
-
-            let payloadHtml = "@";
-            switch (expr.builtinBin.name) {
-              case "float_to_int": {
-                payloadHtml += "floatToInt";
-                break;
-              }
-              case "int_to_float": {
-                payloadHtml += "intToFloat";
-                break;
-              }
-              case "int_to_ptr": {
-                payloadHtml += "intToPtr";
-                break;
-              }
-              case "int_to_enum": {
-                payloadHtml += "intToEnum";
-                break;
-              }
-              case "float_cast": {
-                payloadHtml += "floatCast";
-                break;
-              }
-              case "int_cast": {
-                payloadHtml += "intCast";
-                break;
-              }
-              case "ptr_cast": {
-                payloadHtml += "ptrCast";
-                break;
-              }
-              case "truncate": {
-                payloadHtml += "truncate";
-                break;
-              }
-              case "align_cast": {
-                payloadHtml += "alignCast";
-                break;
-              }
-              case "has_decl": {
-                payloadHtml += "hasDecl";
-                break;
-              }
-              case "has_field": {
-                payloadHtml += "hasField";
-                break;
-              }
-              case "bit_reverse": {
-                payloadHtml += "bitReverse";
-                break;
-              }
-              case "div_exact": {
-                payloadHtml +=  "divExact"; 
-                break;
-              }
-              case "div_floor": {
-                payloadHtml +=  "divFloor"; 
-                break;
-              }
-              case "div_trunc": {
-                payloadHtml +=  "divTrunc"; 
-                break;
-              }
-              case "mod": {
-                payloadHtml +=  "mod"; 
-                break;
-              }
-              case "rem": {
-                payloadHtml +=  "rem"; 
-                break;
-              }
-              case "mod_rem": {
-                payloadHtml +=  "rem"; 
-                break;
-              }
-              case "shl_exact": {
-                payloadHtml +=  "shlExact"; 
-                break;
-              }
-              case "shr_exact": {
-                payloadHtml +=  "shrExact"; 
-                break;
-              }
-              case "bitcast" : {
-                payloadHtml +=  "bitCast"; 
-                break;
-              }
-              case "align_cast" : {
-                payloadHtml +=  "alignCast"; 
-                break;
-              }
-              case "vector_type" : {
-                payloadHtml +=  "Vector"; 
-                break;
-              }
-              case "reduce": {
-                payloadHtml +=  "reduce"; 
-                break;
-              }
-              case "splat": {
-                payloadHtml +=  "splat"; 
-                break;
-              }
-              case "offset_of": {
-                payloadHtml +=  "offsetOf"; 
-                break;
-              }
-              case "bit_offset_of": {
-                payloadHtml +=  "bitOffsetOf"; 
-                break;
-              }
-              default: console.log("builtin function not handled yet or doesn't exist!");
-            };
-            return payloadHtml + "(" + lhs + ", " + rhs + ")";
-
+          case "fabs": {
+            payloadHtml += "fabs";
+            break;
           }
-          case "binOpIndex" : {
-            const binOpIndex = zigAnalysis.exprs[expr.binOpIndex];
-            return exprName(binOpIndex, opts);
+          case "floor": {
+            payloadHtml += "floor";
+            break;
           }
-          case "binOp": {
-            const lhsOp = zigAnalysis.exprs[expr.binOp.lhs];
-            const rhsOp = zigAnalysis.exprs[expr.binOp.rhs];
-            let lhs = exprName(lhsOp, opts);
-            let rhs = exprName(rhsOp, opts);
-
-            let print_lhs = "";
-            let print_rhs = "";
-
-            if (lhsOp['binOpIndex']) {
-              print_lhs = "(" + lhs + ")";
-            } else {
-              print_lhs = lhs;
-            }
-            if (rhsOp['binOpIndex']) {
-              print_rhs = "(" + rhs + ")";
-            } else {
-              print_rhs = rhs;
-            }
-
-            let operator = "";
-
-            switch (expr.binOp.name) {
-              case "add": {
-                operator += "+";
-                break;
-              }
-              case "addwrap": {
-                operator += "+%";
-                break;
-              }
-              case "add_sat": {
-                operator += "+|";
-                break;
-              }
-              case "sub": {
-                operator += "-";
-                break;
-              }
-              case "subwrap": {
-                operator += "-%";
-                break;
-              }
-              case "sub_sat": {
-                operator += "-|";
-                break;
-              }
-              case "mul": {
-                operator += "*";
-                break;
-              }
-              case "mulwrap": {
-                operator += "*%";
-                break;
-              }
-              case "mul_sat": {
-                operator += "*|";
-                break;
-              }
-              case "div": {
-                operator += "/";
-                break;
-              }
-              case "shl": {
-                operator += "<<";
-                break;
-              }
-              case "shl_sat": {
-                operator += "<<|";
-                break;
-              }
-              case "shr": {
-                operator += ">>";
-                break;
-              }
-              case "bit_or" : {
-                operator += "|";
-                break;
-              }
-              case "bit_and" : {
-                operator += "&";
-                break;
-              }
-              case "array_cat" : {
-                operator += "++";
-                break;
-              }
-              case "array_mul" : {
-                operator += "**";
-                break;
-              }
-              default: console.log("operator not handled yet or doesn't exist!");
-            };
-
-            return print_lhs + " " + operator + " " + print_rhs;
-
+          case "ceil": {
+            payloadHtml += "ceil";
+            break;
           }
-          case "errorSets": {
-            const errUnionObj = zigAnalysis.types[expr.errorSets];
-            let lhs = exprName(errUnionObj.lhs, opts);
-            let rhs = exprName(errUnionObj.rhs, opts);
-            return lhs + " || " + rhs;
-
+          case "trunc": {
+            payloadHtml += "trunc";
+            break;
           }
-          case "errorUnion": {
-            const errUnionObj = zigAnalysis.types[expr.errorUnion];
-            let lhs = exprName(errUnionObj.lhs, opts);
-            let rhs = exprName(errUnionObj.rhs, opts);
-            return lhs + "!" + rhs;
-
+          case "round": {
+            payloadHtml += "round";
+            break;
           }
-          case "struct": {
-            const struct_name = zigAnalysis.decls[expr.struct[0].val.typeRef.refPath[0].declRef].name;
-            let struct_body = "";
-            struct_body += struct_name + "{ ";
-            for (let i = 0; i < expr.struct.length; i++) {
-              const val = expr.struct[i].name
-              const exprArg = zigAnalysis.exprs[expr.struct[i].val.expr.as.exprArg];
-              let value_field = exprArg[Object.keys(exprArg)[0]];
-              if (value_field instanceof Object) {
-                value_field = zigAnalysis.decls[value_field[0].val.typeRef.refPath[0].declRef].name;
-              };
-              struct_body += "." + val + " = " + value_field;
-              if (i !== expr.struct.length - 1) {
-                struct_body += ", ";
-              }  else {
-                struct_body += " ";
-              }
-            }
-              struct_body += "}";
-            return struct_body;
-          }
-          case "typeOf_peer": {
-            let payloadHtml = "@TypeOf("
-            for (let i = 0; i < expr.typeOf_peer.length; i++) {
-              let elem = zigAnalysis.exprs[expr.typeOf_peer[i]];
-              payloadHtml += exprName(elem, {wantHtml: true, wantLink:true});
-              if (i !== expr.typeOf_peer.length - 1) {
-                payloadHtml += ", ";
-              }
-            }
-            payloadHtml += ")";
-            return payloadHtml;
-
+          case "tag_name": {
+            payloadHtml += "tagName";
+            break;
           }
-          case "alignOf": {
-            const alignRefArg = zigAnalysis.exprs[expr.alignOf];
-            let payloadHtml = "@alignOf(" + exprName(alignRefArg, {wantHtml: true, wantLink:true}) + ")";
-            return payloadHtml;
+          case "reify": {
+            payloadHtml += "Type";
+            break;
           }
-          case "typeOf": {
-            const typeRefArg = zigAnalysis.exprs[expr.typeOf];
-            let payloadHtml = "@TypeOf(" + exprName(typeRefArg, {wantHtml: true, wantLink:true}) + ")";
-            return payloadHtml;
+          case "type_name": {
+            payloadHtml += "typeName";
+            break;
           }
-          case "typeInfo": {
-            const typeRefArg = zigAnalysis.exprs[expr.typeInfo];
-            let payloadHtml = "@typeInfo(" + exprName(typeRefArg, {wantHtml: true, wantLink:true}) + ")";
-            return payloadHtml;
+          case "frame_type": {
+            payloadHtml += "Frame";
+            break;
           }
-          case "null": {
-            return "null";
+          case "frame_size": {
+            payloadHtml += "frameSize";
+            break;
           }
-          case "array": {
-            let payloadHtml = ".{";
-            for (let i = 0; i < expr.array.length; i++) {
-                if (i != 0) payloadHtml += ", ";
-                let elem = zigAnalysis.exprs[expr.array[i]];
-                payloadHtml += exprName(elem, opts);
-            }
-            return payloadHtml + "}";
+          case "ptr_to_int": {
+            payloadHtml += "ptrToInt";
+            break;
           }
-          case "comptimeExpr": {
-              return zigAnalysis.comptimeExprs[expr.comptimeExpr].code;
+          case "error_to_int": {
+            payloadHtml += "errorToInt";
+            break;
           }
-          case "call": {
-              let call = zigAnalysis.calls[expr.call];
-              let payloadHtml = "";
-
-
-              switch(Object.keys(call.func)[0]){
-                default: throw "TODO";
-                case "declRef":
-                case "refPath": {
-                    payloadHtml += exprName(call.func, opts);
-                    break;
-                }
-              }
-              payloadHtml += "(";
-
-              for (let i = 0; i < call.args.length; i++) {
-                  if (i != 0) payloadHtml += ", ";
-                  payloadHtml += exprName(call.args[i], opts);
-              }
-
-              payloadHtml += ")";
-              return payloadHtml;
+          case "int_to_error": {
+            payloadHtml += "intToError";
+            break;
           }
-          case "as": {
-            // @Check : this should be done in backend because there are legit @as() calls
-              // const typeRefArg = zigAnalysis.exprs[expr.as.typeRefArg];
-              const exprArg = zigAnalysis.exprs[expr.as.exprArg];
-              // return "@as(" + exprName(typeRefArg, opts) +
-              //   ", " + exprName(exprArg, opts) + ")";
-              return exprName(exprArg, opts);
+          case "maximum": {
+            payloadHtml += "maximum";
+            break;
           }
-          case "declRef": {
-            return zigAnalysis.decls[expr.declRef].name;
+          case "minimum": {
+            payloadHtml += "minimum";
+            break;
           }
-          case "refPath": {
-            return expr.refPath.map(x => exprName(x, opts)).join(".");
+          case "bit_not": {
+            return "~" + param;
           }
-          case "int": {
-              return "" + expr.int;
+          case "clz": {
+            return "@clz(T" + ", " + param + ")";
           }
-          case "float": {
-              return "" + expr.float.toFixed(2);
+          case "ctz": {
+            return "@ctz(T" + ", " + param + ")";
           }
-          case "float128": {
-              return "" + expr.float128.toFixed(2);
+          case "pop_count": {
+            return "@popCount(T" + ", " + param + ")";
           }
-          case "undefined": {
-              return "undefined";
+          case "byte_swap": {
+            return "@byteSwap(T" + ", " + param + ")";
           }
-          case "string": {
-            return "\"" + escapeHtml(expr.string) + "\"";
+          case "bit_reverse": {
+            return "@bitReverse(T" + ", " + param + ")";
           }
-
-          case "anytype": {
-            return "anytype";
+          default:
+            console.log("builtin function not handled yet or doesn't exist!");
+        }
+        return payloadHtml + "(" + param + ")";
+      }
+      case "builtinBinIndex": {
+        const builtinBinIndex = zigAnalysis.exprs[expr.builtinBinIndex];
+        return exprName(builtinBinIndex, opts);
+      }
+      case "builtinBin": {
+        const lhsOp = zigAnalysis.exprs[expr.builtinBin.lhs];
+        const rhsOp = zigAnalysis.exprs[expr.builtinBin.rhs];
+        let lhs = exprName(lhsOp, opts);
+        let rhs = exprName(rhsOp, opts);
+
+        let payloadHtml = "@";
+        switch (expr.builtinBin.name) {
+          case "float_to_int": {
+            payloadHtml += "floatToInt";
+            break;
           }
-
-          case "this":{
-            return "@This()";
+          case "int_to_float": {
+            payloadHtml += "intToFloat";
+            break;
           }
+          case "int_to_ptr": {
+            payloadHtml += "intToPtr";
+            break;
+          }
+          case "int_to_enum": {
+            payloadHtml += "intToEnum";
+            break;
+          }
+          case "float_cast": {
+            payloadHtml += "floatCast";
+            break;
+          }
+          case "int_cast": {
+            payloadHtml += "intCast";
+            break;
+          }
+          case "ptr_cast": {
+            payloadHtml += "ptrCast";
+            break;
+          }
+          case "truncate": {
+            payloadHtml += "truncate";
+            break;
+          }
+          case "align_cast": {
+            payloadHtml += "alignCast";
+            break;
+          }
+          case "has_decl": {
+            payloadHtml += "hasDecl";
+            break;
+          }
+          case "has_field": {
+            payloadHtml += "hasField";
+            break;
+          }
+          case "bit_reverse": {
+            payloadHtml += "bitReverse";
+            break;
+          }
+          case "div_exact": {
+            payloadHtml += "divExact";
+            break;
+          }
+          case "div_floor": {
+            payloadHtml += "divFloor";
+            break;
+          }
+          case "div_trunc": {
+            payloadHtml += "divTrunc";
+            break;
+          }
+          case "mod": {
+            payloadHtml += "mod";
+            break;
+          }
+          case "rem": {
+            payloadHtml += "rem";
+            break;
+          }
+          case "mod_rem": {
+            payloadHtml += "rem";
+            break;
+          }
+          case "shl_exact": {
+            payloadHtml += "shlExact";
+            break;
+          }
+          case "shr_exact": {
+            payloadHtml += "shrExact";
+            break;
+          }
+          case "bitcast": {
+            payloadHtml += "bitCast";
+            break;
+          }
+          case "align_cast": {
+            payloadHtml += "alignCast";
+            break;
+          }
+          case "vector_type": {
+            payloadHtml += "Vector";
+            break;
+          }
+          case "reduce": {
+            payloadHtml += "reduce";
+            break;
+          }
+          case "splat": {
+            payloadHtml += "splat";
+            break;
+          }
+          case "offset_of": {
+            payloadHtml += "offsetOf";
+            break;
+          }
+          case "bit_offset_of": {
+            payloadHtml += "bitOffsetOf";
+            break;
+          }
+          default:
+            console.log("builtin function not handled yet or doesn't exist!");
+        }
+        return payloadHtml + "(" + lhs + ", " + rhs + ")";
+      }
+      case "binOpIndex": {
+        const binOpIndex = zigAnalysis.exprs[expr.binOpIndex];
+        return exprName(binOpIndex, opts);
+      }
+      case "binOp": {
+        const lhsOp = zigAnalysis.exprs[expr.binOp.lhs];
+        const rhsOp = zigAnalysis.exprs[expr.binOp.rhs];
+        let lhs = exprName(lhsOp, opts);
+        let rhs = exprName(rhsOp, opts);
 
-          case "type": {
-              let name = "";
-
-              let typeObj = expr.type;
-              if (typeof typeObj === 'number') typeObj = zigAnalysis.types[typeObj];
-              switch (typeObj.kind) {
-                  default: throw "TODO";
-                  case typeKinds.Struct:
-                  {
-                    let structObj =  (typeObj);
-                    return structObj;
-                  }
-                  case typeKinds.Enum:
-                  {
-                    let enumObj =  (typeObj);
-                    return enumObj;
-                  }
-                  case typeKinds.Opaque:
-                  {
-                    let opaqueObj =  (typeObj);
-
-                    return opaqueObj.name;
-                  }
-                  case typeKinds.ComptimeExpr:
-                  {
-                      return "anyopaque";
-                  }
-                  case typeKinds.Array:
-                  {
-                    let arrayObj = typeObj;
-                    let name = "[";
-                    let lenName = exprName(arrayObj.len, opts);
-                    let sentinel = arrayObj.sentinel ? ":"+exprName(arrayObj.sentinel, opts) : "";
-                    // let is_mutable = arrayObj.is_multable ? "const " : "";
-
-                    if (opts.wantHtml) {
-                      name +=
-                        '<span class="tok-number">' + lenName + sentinel + "</span>";
-                    } else {
-                      name += lenName + sentinel;
-                    }
-                    name += "]";
-                    // name += is_mutable;
-                    name += exprName(arrayObj.child, opts);
-                    return name;
-                  }
-                  case typeKinds.Optional:
-                      return "?" + exprName((typeObj).child, opts);
-                  case typeKinds.Pointer:
-                  {
-                      let ptrObj = (typeObj);
-                    let sentinel = ptrObj.sentinel ? ":"+exprName(ptrObj.sentinel, opts) : "";
-                      let is_mutable = !ptrObj.is_mutable ? "const " : "";
-                      let name = "";
-                      switch (ptrObj.size) {
-                          default:
-                              console.log("TODO: implement unhandled pointer size case");
-                          case pointerSizeEnum.One:
-                              name += "*";
-                              name += is_mutable;
-                              break;
-                          case pointerSizeEnum.Many:
-                              name += "[*";
-                              name += sentinel;
-                              name += "]";
-                              name += is_mutable;
-                              break;
-                          case pointerSizeEnum.Slice:
-                              if (ptrObj.is_ref) {
-                                name += "*";
-                              }
-                              name += "[";
-                              name += sentinel;
-                              name += "]";
-                              name += is_mutable;
-                              break;
-                          case pointerSizeEnum.C:
-                              name += "[*c";
-                              name += sentinel;
-                              name += "]";
-                              name += is_mutable;
-                              break;
-                      }
-                      // @check: after the major changes in arrays the consts are came from switch above
-                      // if (!ptrObj.is_mutable) {
-                      //     if (opts.wantHtml) {
-                      //         name += '<span class="tok-kw">const</span> ';
-                      //     } else {
-                      //         name += "const ";
-                      //     }
-                      // }
-                      if (ptrObj.is_allowzero) {
-                              name += "allowzero ";
-                      }
-                      if (ptrObj.is_volatile) {
-                              name += "volatile ";
-                      }
-                      if (ptrObj.has_addrspace) {
-                              name += "addrspace(";
-                              name += "." + "";
-                              name += ") ";
-                      }
-                      if (ptrObj.has_align) {
-                          let align = exprName(ptrObj.align, opts);
-                          if (opts.wantHtml) {
-                              name += '<span class="tok-kw">align</span>(';
-                          } else {
-                              name += "align(";
-                          }
-                          if (opts.wantHtml) {
-                              name += '<span class="tok-number">' + align + '</span>';
-                          } else {
-                              name += align;
-                          }
-                          if (ptrObj.hostIntBytes != null) {
-                              name += ":";
-                              if (opts.wantHtml) {
-                                  name += '<span class="tok-number">' + ptrObj.bitOffsetInHost + '</span>';
-                              } else {
-                                  name += ptrObj.bitOffsetInHost;
-                              }
-                              name += ":";
-                              if (opts.wantHtml) {
-                                  name += '<span class="tok-number">' + ptrObj.hostIntBytes + '</span>';
-                              } else {
-                                  name += ptrObj.hostIntBytes;
-                              }
-                          }
-                          name += ") ";
-                      }
-                      //name += typeValueName(ptrObj.child, wantHtml, wantSubLink, null);
-                      name += exprName(ptrObj.child, opts);
-                      return name;
-                  }
-                  case typeKinds.Float:
-                  {
-                      let floatObj =  (typeObj);
-
-                      if (opts.wantHtml) {
-                          return '<span class="tok-type">' + floatObj.name + '</span>';
-                      } else {
-                          return floatObj.name;
-                      }
-                  }
-                  case typeKinds.Int:
-                  {
-                      let intObj = (typeObj);
-                      let name = intObj.name;
-                      if (opts.wantHtml) {
-                          return '<span class="tok-type">' + name + '</span>';
-                      } else {
-                          return name;
-                      }
-                  }
-                  case typeKinds.ComptimeInt:
-                      if (opts.wantHtml) {
-                          return '<span class="tok-type">comptime_int</span>';
-                      } else {
-                          return "comptime_int";
-                      }
-                  case typeKinds.ComptimeFloat:
-                      if (opts.wantHtml) {
-                          return '<span class="tok-type">comptime_float</span>';
-                      } else {
-                          return "comptime_float";
-                      }
-                  case typeKinds.Type:
-                      if (opts.wantHtml) {
-                          return '<span class="tok-type">type</span>';
-                      } else {
-                          return "type";
-                      }
-                  case typeKinds.Bool:
-                      if (opts.wantHtml) {
-                          return '<span class="tok-type">bool</span>';
-                      } else {
-                          return "bool";
-                      }
-                  case typeKinds.Void:
-                      if (opts.wantHtml) {
-                          return '<span class="tok-type">void</span>';
-                      } else {
-                          return "void";
-                      }
-                  case typeKinds.EnumLiteral:
-                      if (opts.wantHtml) {
-                          return '<span class="tok-type">(enum literal)</span>';
-                      } else {
-                          return "(enum literal)";
-                      }
-                  case typeKinds.NoReturn:
-                      if (opts.wantHtml) {
-                          return '<span class="tok-type">noreturn</span>';
-                      } else {
-                          return "noreturn";
-                      }
-                  case typeKinds.ErrorSet:
-                  {
-                      let errSetObj = (typeObj);
-                      if (errSetObj.fields == null) {
-                              return '<span class="tok-type">anyerror</span>';
-                      } else {
-                          // throw "TODO";
-                        let html = "error{" + errSetObj.fields[0].name + "}";
-                        return html;
-                      }
-                  }
-
-                  case typeKinds.ErrorUnion:
-                  {
-                    let errUnionObj = (typeObj);
-                    let lhs = exprName(errUnionObj.lhs, opts);
-                    let rhs = exprName(errUnionObj.rhs, opts);
-                    return lhs + "!" + rhs;
-                  }
-                  case typeKinds.InferredErrorUnion:
-                  {
-                    let errUnionObj = (typeObj);
-                    let payload = exprName(errUnionObj.payload, opts);
-                    return "!" + payload;
-                  }
-                  case typeKinds.Fn:
-                  {
-                      let fnObj = (typeObj);
-                      let payloadHtml = "";
-                      if (opts.wantHtml) {
-                          if (fnObj.is_extern) {
-                            payloadHtml += "pub extern ";
-                          }
-                          if (fnObj.has_lib_name) {
-                            payloadHtml += "\"" + fnObj.lib_name +"\" ";
-                          }
-                          payloadHtml += '<span class="tok-kw">fn</span>';
-                          if (opts.fnDecl) {
-                              payloadHtml += ' <span class="tok-fn">';
-                              if (opts.linkFnNameDecl) {
-                                  payloadHtml += '<a href="' + opts.linkFnNameDecl + '">' +
-                                      escapeHtml(opts.fnDecl.name) + '</a>';
-                              } else {
-                                  payloadHtml += escapeHtml(opts.fnDecl.name);
-                              }
-                              payloadHtml += '</span>';
-                          }
-                      } else {
-                          payloadHtml += 'fn ';
-                      }
-                      payloadHtml += '(';
-                          if (fnObj.params) {
-                              let fields = null;
-                              let isVarArgs = false;
-                              let fnNode = zigAnalysis.astNodes[fnObj.src];
-                              fields = fnNode.fields;
-                              isVarArgs = fnNode.varArgs;
-
-                              for (let i = 0; i < fnObj.params.length; i += 1) {
-                                  if (i != 0) {
-                                      payloadHtml += ', ';
-                                  }
-
-                                  payloadHtml += "<span class='argBreaker'><br>&nbsp;&nbsp;&nbsp;&nbsp;</span>"
-                                  let value = fnObj.params[i];
-                                  let paramValue = resolveValue({expr: value});
-
-                                  if (fields != null) {
-                                      let paramNode = zigAnalysis.astNodes[fields[i]];
-
-                                      if (paramNode.varArgs) {
-                                          payloadHtml += '...';
-                                          continue;
-                                      }
-
-                                      if (paramNode.noalias) {
-                                          if (opts.wantHtml) {
-                                              payloadHtml += '<span class="tok-kw">noalias</span> ';
-                                          } else {
-                                              payloadHtml += 'noalias ';
-                                          }
-                                      }
-
-                                      if (paramNode.comptime) {
-                                          if (opts.wantHtml) {
-                                              payloadHtml += '<span class="tok-kw">comptime</span> ';
-                                          } else {
-                                              payloadHtml += 'comptime ';
-                                          }
-                                      }
-
-                                      let paramName = paramNode.name;
-                                      if (paramName != null) {
-                                          // skip if it matches the type name
-                                          if (!shouldSkipParamName(paramValue, paramName)) {
-                                              payloadHtml += paramName + ': ';
-                                          }
-                                      }
-                                  }
-
-                                  if (isVarArgs && i === fnObj.params.length - 1) {
-                                      payloadHtml += '...';
-                                  }
-                                  else if ("alignOf" in value) {
-                                    if (opts.wantHtml) {
-                                      payloadHtml += '<a href="">';
-                                      payloadHtml +=
-                                        '<span class="tok-kw" style="color:lightblue;">'
-                                        + exprName(value, opts) + '</span>';
-                                      payloadHtml += '</a>';
-                                    } else {
-                                      payloadHtml += exprName(value, opts);
-                                    }
-
-                                  }
-                                  else if ("typeOf" in value) {
-                                    if (opts.wantHtml) {
-                                      payloadHtml += '<a href="">';
-                                      payloadHtml +=
-                                        '<span class="tok-kw" style="color:lightblue;">'
-                                        + exprName(value, opts) + '</span>';
-                                      payloadHtml += '</a>';
-                                    } else {
-                                      payloadHtml += exprName(value, opts);
-                                    }
-
-                                  }
-                                  else if ("typeOf_peer" in value) {
-                                    if (opts.wantHtml) {
-                                      payloadHtml += '<a href="">';
-                                      payloadHtml +=
-                                        '<span class="tok-kw" style="color:lightblue;">'
-                                        + exprName(value, opts) + '</span>';
-                                      payloadHtml += '</a>';
-                                    } else {
-                                      payloadHtml += exprName(value, opts);
-                                    }
-
-                                  }
-                                  else if ("declRef" in value) {
-                                    if (opts.wantHtml) {
-                                      payloadHtml += '<a href="">';
-                                      payloadHtml +=
-                                        '<span class="tok-kw" style="color:lightblue;">'
-                                        + exprName(value, opts) + '</span>';
-                                      payloadHtml += '</a>';
-                                    } else {
-                                      payloadHtml += exprName(value, opts);
-                                    }
-
-                                  }
-                                  else if ("call" in value) {
-                                    if (opts.wantHtml) {
-                                      payloadHtml += '<a href="">';
-                                      payloadHtml +=
-                                        '<span class="tok-kw" style="color:lightblue;">'
-                                        + exprName(value, opts) + '</span>';
-                                      payloadHtml += '</a>';
-                                    } else {
-                                      payloadHtml += exprName(value, opts);
-                                    }
-                                  }
-                                  else if ("refPath" in value) {
-                                    if (opts.wantHtml) {
-                                      payloadHtml += '<a href="">';
-                                      payloadHtml +=
-                                        '<span class="tok-kw" style="color:lightblue;">'
-                                        + exprName(value, opts) + '</span>';
-                                      payloadHtml += '</a>';
-                                    } else {
-                                      payloadHtml += exprName(value, opts);
-                                    }
-                                  } else if ("type" in value) {
-                                      let name = exprName(value, {
-                                        wantHtml: false,
-                                        wantLink: false,
-                                        fnDecl: opts.fnDecl,
-                                        linkFnNameDecl: opts.linkFnNameDecl,
-                                      });
-                                      payloadHtml += '<span class="tok-kw">' + name + '</span>';
-                                  } else if ("binOpIndex" in value) {
-                                    payloadHtml += exprName(value, opts);
-                                  }else if ("comptimeExpr" in value) {
-                                      let comptimeExpr = zigAnalysis.comptimeExprs[value.comptimeExpr].code;
-                                      if (opts.wantHtml) {
-                                        payloadHtml += '<span class="tok-kw">' + comptimeExpr + '</span>';
-                                      } else {
-                                        payloadHtml += comptimeExpr;
-                                      }
-                                  } else if (opts.wantHtml) {
-                                      payloadHtml += '<span class="tok-kw">anytype</span>';
-                                  } else {
-                                      payloadHtml += 'anytype';
-                                  }
-                              }
-                          }
-
-                      payloadHtml += "<span class='argBreaker'>,<br></span>"
-                      payloadHtml += ') ';
-
-                    if (fnObj.has_align) {
-                      let align = zigAnalysis.exprs[fnObj.align]
-                      payloadHtml += "align(" + exprName(align, opts) + ") ";
-                    }
-                    if (fnObj.has_cc) {
-                      let cc = zigAnalysis.exprs[fnObj.cc]
-                      if (cc) {
-                        payloadHtml += "callconv(." + cc.enumLiteral + ") ";
-                      }
-                    }
+        let print_lhs = "";
+        let print_rhs = "";
 
-                      if (fnObj.is_inferred_error) {
-                          payloadHtml += "!";
-                      }
-                      if (fnObj.ret != null) {
-                          payloadHtml += exprName(fnObj.ret, opts);
-                      } else if (opts.wantHtml) {
-                          payloadHtml += '<span class="tok-kw">anytype</span>';
-                      } else {
-                          payloadHtml += 'anytype';
-                      }
-                      return payloadHtml;
-                  }
-                      // if (wantHtml) {
-                      //     return escapeHtml(typeObj.name);
-                      // } else {
-                      //     return typeObj.name;
-                      // }
-              }
+        if (lhsOp["binOpIndex"]) {
+          print_lhs = "(" + lhs + ")";
+        } else {
+          print_lhs = lhs;
         }
-
+        if (rhsOp["binOpIndex"]) {
+          print_rhs = "(" + rhs + ")";
+        } else {
+          print_rhs = rhs;
         }
-    }
 
+        let operator = "";
 
-    
-    function shouldSkipParamName(typeRef, paramName) {
-        let resolvedTypeRef = resolveValue({expr: typeRef});
-        if ("type" in resolvedTypeRef) {
-            let typeObj = zigAnalysis.types[resolvedTypeRef.type];
-            if (typeObj.kind === typeKinds.Pointer){
-                let ptrObj = (typeObj);
-                if (getPtrSize(ptrObj) === pointerSizeEnum.One) {
-                    const value = resolveValue(ptrObj.child);
-                    return typeValueName(value, false, true).toLowerCase() === paramName;
-                }
-            }
+        switch (expr.binOp.name) {
+          case "add": {
+            operator += "+";
+            break;
+          }
+          case "addwrap": {
+            operator += "+%";
+            break;
+          }
+          case "add_sat": {
+            operator += "+|";
+            break;
+          }
+          case "sub": {
+            operator += "-";
+            break;
+          }
+          case "subwrap": {
+            operator += "-%";
+            break;
+          }
+          case "sub_sat": {
+            operator += "-|";
+            break;
+          }
+          case "mul": {
+            operator += "*";
+            break;
+          }
+          case "mulwrap": {
+            operator += "*%";
+            break;
+          }
+          case "mul_sat": {
+            operator += "*|";
+            break;
+          }
+          case "div": {
+            operator += "/";
+            break;
+          }
+          case "shl": {
+            operator += "<<";
+            break;
+          }
+          case "shl_sat": {
+            operator += "<<|";
+            break;
+          }
+          case "shr": {
+            operator += ">>";
+            break;
+          }
+          case "bit_or": {
+            operator += "|";
+            break;
+          }
+          case "bit_and": {
+            operator += "&";
+            break;
+          }
+          case "array_cat": {
+            operator += "++";
+            break;
+          }
+          case "array_mul": {
+            operator += "**";
+            break;
+          }
+          default:
+            console.log("operator not handled yet or doesn't exist!");
         }
-        return false;
-    }
 
-    
-    function getPtrSize(typeObj) {
-        return (typeObj.size == null) ? pointerSizeEnum.One : typeObj.size;
-    }
-
-    
-    function renderType(typeObj) {
-        let name;
-        if (rootIsStd && typeObj === zigAnalysis.types[zigAnalysis.packages[zigAnalysis.rootPkg].main]) {
-            name = "std";
-        } else {
-            name = exprName({type:typeObj}, false, false);
-        }
-        if (name != null && name != "") {
-            domHdrName.innerText = name + " (" + zigAnalysis.typeKinds[typeObj.kind] + ")";
-            domHdrName.classList.remove("hidden");
-        }
-        if (typeObj.kind == typeKinds.ErrorSet) {
-            renderErrorSet((typeObj));
+        return print_lhs + " " + operator + " " + print_rhs;
+      }
+      case "errorSets": {
+        const errUnionObj = zigAnalysis.types[expr.errorSets];
+        let lhs = exprName(errUnionObj.lhs, opts);
+        let rhs = exprName(errUnionObj.rhs, opts);
+        return lhs + " || " + rhs;
+      }
+      case "errorUnion": {
+        const errUnionObj = zigAnalysis.types[expr.errorUnion];
+        let lhs = exprName(errUnionObj.lhs, opts);
+        let rhs = exprName(errUnionObj.rhs, opts);
+        return lhs + "!" + rhs;
+      }
+      case "struct": {
+        const struct_name =
+          zigAnalysis.decls[expr.struct[0].val.typeRef.refPath[0].declRef].name;
+        let struct_body = "";
+        struct_body += struct_name + "{ ";
+        for (let i = 0; i < expr.struct.length; i++) {
+          const val = expr.struct[i].name;
+          const exprArg = zigAnalysis.exprs[expr.struct[i].val.expr.as.exprArg];
+          let value_field = exprArg[Object.keys(exprArg)[0]];
+          if (value_field instanceof Object) {
+            value_field =
+              zigAnalysis.decls[value_field[0].val.typeRef.refPath[0].declRef]
+                .name;
+          }
+          struct_body += "." + val + " = " + value_field;
+          if (i !== expr.struct.length - 1) {
+            struct_body += ", ";
+          } else {
+            struct_body += " ";
+          }
         }
-    }
-
-    
-    function renderErrorSet(errSetType) {
-        if (errSetType.fields == null) {
-            domFnErrorsAnyError.classList.remove("hidden");
-        } else {
-            let errorList = [];
-            for (let i = 0; i < errSetType.fields.length; i += 1) {
-                let errObj = errSetType.fields[i];
-                //let srcObj = zigAnalysis.astNodes[errObj.src];
-                errorList.push(errObj);
-            }
-            errorList.sort(function(a, b) {
-                return operatorCompare(a.name.toLowerCase(), b.name.toLowerCase());
-            });
-
-            resizeDomListDl(domListFnErrors, errorList.length);
-            for (let i = 0; i < errorList.length; i += 1) {
-                let nameTdDom = domListFnErrors.children[i * 2 + 0];
-                let descTdDom = domListFnErrors.children[i * 2 + 1];
-                nameTdDom.textContent = errorList[i].name;
-                let docs = errorList[i].docs;
-                if (docs != null) {
-                    descTdDom.innerHTML = markdown(docs);
-                } else {
-                    descTdDom.textContent = "";
-                }
-            }
-            domTableFnErrors.classList.remove("hidden");
+        struct_body += "}";
+        return struct_body;
+      }
+      case "typeOf_peer": {
+        let payloadHtml = "@TypeOf(";
+        for (let i = 0; i < expr.typeOf_peer.length; i++) {
+          let elem = zigAnalysis.exprs[expr.typeOf_peer[i]];
+          payloadHtml += exprName(elem, { wantHtml: true, wantLink: true });
+          if (i !== expr.typeOf_peer.length - 1) {
+            payloadHtml += ", ";
+          }
         }
-        domSectFnErrors.classList.remove("hidden");
-    }
-
-//     function allCompTimeFnCallsHaveTypeResult(typeIndex, value) {
-//         let srcIndex = zigAnalysis.fns[value].src;
-//         let calls = nodesToCallsMap[srcIndex];
-//         if (calls == null) return false;
-//         for (let i = 0; i < calls.length; i += 1) {
-//             let call = zigAnalysis.calls[calls[i]];
-//             if (call.result.type !== typeTypeId) return false;
-//         }
-//         return true;
-//     }
-//
-//     function allCompTimeFnCallsResult(calls) {
-//         let firstTypeObj = null;
-//         let containerObj = {
-//             privDecls: [],
-//         };
-//         for (let callI = 0; callI < calls.length; callI += 1) {
-//             let call = zigAnalysis.calls[calls[callI]];
-//             if (call.result.type !== typeTypeId) return null;
-//             let typeObj = zigAnalysis.types[call.result.value];
-//             if (!typeKindIsContainer(typeObj.kind)) return null;
-//             if (firstTypeObj == null) {
-//                 firstTypeObj = typeObj;
-//                 containerObj.src = typeObj.src;
-//             } else if (firstTypeObj.src !== typeObj.src) {
-//                 return null;
-//             }
-//
-//             if (containerObj.fields == null) {
-//                 containerObj.fields = (typeObj.fields || []).concat([]);
-//             } else for (let fieldI = 0; fieldI < typeObj.fields.length; fieldI += 1) {
-//                 let prev = containerObj.fields[fieldI];
-//                 let next = typeObj.fields[fieldI];
-//                 if (prev === next) continue;
-//                 if (typeof(prev) === 'object') {
-//                     if (prev[next] == null) prev[next] = typeObj;
-//                 } else {
-//                     containerObj.fields[fieldI] = {};
-//                     containerObj.fields[fieldI][prev] = firstTypeObj;
-//                     containerObj.fields[fieldI][next] = typeObj;
-//                 }
-//             }
-//
-//             if (containerObj.pubDecls == null) {
-//                 containerObj.pubDecls = (typeObj.pubDecls || []).concat([]);
-//             } else for (let declI = 0; declI < typeObj.pubDecls.length; declI += 1) {
-//                 let prev = containerObj.pubDecls[declI];
-//                 let next = typeObj.pubDecls[declI];
-//                 if (prev === next) continue;
-//                 // TODO instead of showing "examples" as the public declarations,
-//                     // do logic like this:
-//                 //if (typeof(prev) !== 'object') {
-//                     //    let newDeclId = zigAnalysis.decls.length;
-//                     //    prev = clone(zigAnalysis.decls[prev]);
-//                     //    prev.id = newDeclId;
-//                     //    zigAnalysis.decls.push(prev);
-//                     //    containerObj.pubDecls[declI] = prev;
-//                     //}
-//                 //mergeDecls(prev, next, firstTypeObj, typeObj);
-//             }
-//         }
-//         for (let declI = 0; declI < containerObj.pubDecls.length; declI += 1) {
-//             let decl = containerObj.pubDecls[declI];
-//             if (typeof(decl) === 'object') {
-//                 containerObj.pubDecls[declI] = containerObj.pubDecls[declI].id;
-//             }
-//         }
-//         return containerObj;
-//     }
-
-
-
-    
-    function renderValue(decl) {
-        let resolvedValue = resolveValue(decl.value)
-
-      if (resolvedValue.expr.fieldRef) {
-        const declRef = decl.value.expr.refPath[0].declRef;
-        const type = zigAnalysis.decls[declRef];
-        domFnProtoCode.innerHTML = '<span class="tok-kw">const</span> ' +
-          escapeHtml(decl.name) + ': ' + type.name +
-          " = " + exprName(decl.value.expr, {wantHtml: true, wantLink:true}) + ";";
-      } else if (resolvedValue.expr.string !== undefined || resolvedValue.expr.call !== undefined || resolvedValue.expr.comptimeExpr) {
-        domFnProtoCode.innerHTML = '<span class="tok-kw">const</span> ' +
-          escapeHtml(decl.name) + ': ' + exprName(resolvedValue.expr, {wantHtml: true, wantLink:true}) +
-          " = " + exprName(decl.value.expr, {wantHtml: true, wantLink:true}) + ";";
-      } else if (resolvedValue.expr.compileError) {
-        domFnProtoCode.innerHTML = '<span class="tok-kw">const</span> ' +
-          escapeHtml(decl.name) + " = " + exprName(decl.value.expr, {wantHtml: true, wantLink:true}) + ";";
-      } 
-      else {
-        domFnProtoCode.innerHTML = '<span class="tok-kw">const</span> ' +
-          escapeHtml(decl.name) + ': ' + exprName(resolvedValue.typeRef, {wantHtml: true, wantLink:true}) +
-          " = " + exprName(decl.value.expr, {wantHtml: true, wantLink:true}) + ";";
+        payloadHtml += ")";
+        return payloadHtml;
       }
-
-        let docs = zigAnalysis.astNodes[decl.src].docs;
-        if (docs != null) {
-            domTldDocs.innerHTML = markdown(docs);
-            domTldDocs.classList.remove("hidden");
+      case "alignOf": {
+        const alignRefArg = zigAnalysis.exprs[expr.alignOf];
+        let payloadHtml =
+          "@alignOf(" +
+          exprName(alignRefArg, { wantHtml: true, wantLink: true }) +
+          ")";
+        return payloadHtml;
+      }
+      case "typeOf": {
+        const typeRefArg = zigAnalysis.exprs[expr.typeOf];
+        let payloadHtml =
+          "@TypeOf(" +
+          exprName(typeRefArg, { wantHtml: true, wantLink: true }) +
+          ")";
+        return payloadHtml;
+      }
+      case "typeInfo": {
+        const typeRefArg = zigAnalysis.exprs[expr.typeInfo];
+        let payloadHtml =
+          "@typeInfo(" +
+          exprName(typeRefArg, { wantHtml: true, wantLink: true }) +
+          ")";
+        return payloadHtml;
+      }
+      case "null": {
+        return "null";
+      }
+      case "array": {
+        let payloadHtml = ".{";
+        for (let i = 0; i < expr.array.length; i++) {
+          if (i != 0) payloadHtml += ", ";
+          let elem = zigAnalysis.exprs[expr.array[i]];
+          payloadHtml += exprName(elem, opts);
+        }
+        return payloadHtml + "}";
+      }
+      case "comptimeExpr": {
+        return zigAnalysis.comptimeExprs[expr.comptimeExpr].code;
+      }
+      case "call": {
+        let call = zigAnalysis.calls[expr.call];
+        let payloadHtml = "";
+
+        switch (Object.keys(call.func)[0]) {
+          default:
+            throw "TODO";
+          case "declRef":
+          case "refPath": {
+            payloadHtml += exprName(call.func, opts);
+            break;
+          }
         }
+        payloadHtml += "(";
 
-        domFnProto.classList.remove("hidden");
-    }
-
-    
-    function renderVar(decl) {
-        let declTypeRef = typeOfDecl(decl);
-        domFnProtoCode.innerHTML = '<span class="tok-kw">var</span> ' +
-            escapeHtml(decl.name) + ': ' + typeValueName(declTypeRef, true, true);
-
-        let docs = zigAnalysis.astNodes[decl.src].docs;
-        if (docs != null) {
-            domTldDocs.innerHTML = markdown(docs);
-            domTldDocs.classList.remove("hidden");
+        for (let i = 0; i < call.args.length; i++) {
+          if (i != 0) payloadHtml += ", ";
+          payloadHtml += exprName(call.args[i], opts);
         }
 
-        domFnProto.classList.remove("hidden");
-    }
-
+        payloadHtml += ")";
+        return payloadHtml;
+      }
+      case "as": {
+        // @Check : this should be done in backend because there are legit @as() calls
+        // const typeRefArg = zigAnalysis.exprs[expr.as.typeRefArg];
+        const exprArg = zigAnalysis.exprs[expr.as.exprArg];
+        // return "@as(" + exprName(typeRefArg, opts) +
+        //   ", " + exprName(exprArg, opts) + ")";
+        return exprName(exprArg, opts);
+      }
+      case "declRef": {
+        return zigAnalysis.decls[expr.declRef].name;
+      }
+      case "refPath": {
+        return expr.refPath.map((x) => exprName(x, opts)).join(".");
+      }
+      case "int": {
+        return "" + expr.int;
+      }
+      case "float": {
+        return "" + expr.float.toFixed(2);
+      }
+      case "float128": {
+        return "" + expr.float128.toFixed(2);
+      }
+      case "undefined": {
+        return "undefined";
+      }
+      case "string": {
+        return '"' + escapeHtml(expr.string) + '"';
+      }
 
-    
-    function categorizeDecls(decls,
-        typesList, namespacesList, errSetsList,
-        fnsList, varsList, valsList, testsList) {
+      case "anytype": {
+        return "anytype";
+      }
 
-        for (let i = 0; i < decls.length; i += 1) {
-            let decl = zigAnalysis.decls[decls[i]];
-            let declValue = resolveValue(decl.value);
+      case "this": {
+        return "@This()";
+      }
 
-            if (decl.isTest) {
-                testsList.push(decl);
-                continue;
-            }
+      case "type": {
+        let name = "";
+
+        let typeObj = expr.type;
+        if (typeof typeObj === "number") typeObj = zigAnalysis.types[typeObj];
+        switch (typeObj.kind) {
+          default:
+            throw "TODO";
+          case typeKinds.Struct: {
+            let structObj = typeObj;
+            return structObj;
+          }
+          case typeKinds.Enum: {
+            let enumObj = typeObj;
+            return enumObj;
+          }
+          case typeKinds.Opaque: {
+            let opaqueObj = typeObj;
 
-            if (decl.kind === 'var') {
-                varsList.push(decl);
-                continue;
+            return opaqueObj.name;
+          }
+          case typeKinds.ComptimeExpr: {
+            return "anyopaque";
+          }
+          case typeKinds.Array: {
+            let arrayObj = typeObj;
+            let name = "[";
+            let lenName = exprName(arrayObj.len, opts);
+            let sentinel = arrayObj.sentinel
+              ? ":" + exprName(arrayObj.sentinel, opts)
+              : "";
+            // let is_mutable = arrayObj.is_multable ? "const " : "";
+
+            if (opts.wantHtml) {
+              name +=
+                '<span class="tok-number">' + lenName + sentinel + "</span>";
+            } else {
+              name += lenName + sentinel;
             }
-
-            if (decl.kind === 'const') {
-                if ("type" in declValue.expr) {
-                    // We have the actual type expression at hand.
-                    const typeExpr = zigAnalysis.types[declValue.expr.type];
-                    if (typeExpr.kind == typeKinds.Fn) {
-                        const funcRetExpr = resolveValue({
-                            expr: (typeExpr).ret
-                        });
-                        if ("type" in funcRetExpr.expr && funcRetExpr.expr.type == typeTypeId) {
-                            if (typeIsErrSet(declValue.expr.type)) {
-                                errSetsList.push(decl);
-                            } else if (typeIsStructWithNoFields(declValue.expr.type)) {
-                                namespacesList.push(decl);
-                            } else {
-                                typesList.push(decl);
-                            }
-                        } else {
-                            fnsList.push(decl);
-                        }
-                    } else {
-                        if (typeIsErrSet(declValue.expr.type)) {
-                            errSetsList.push(decl);
-                        } else if (typeIsStructWithNoFields(declValue.expr.type)) {
-                            namespacesList.push(decl);
-                        } else {
-                            typesList.push(decl);
-                        }
-                    }
-                 } else if ("typeRef" in declValue) {
-                      if ("type" in declValue.typeRef && declValue.typeRef == typeTypeId) {
-                          // We don't know what the type expression is, but we know it's a type.
-                          typesList.push(decl);
-                      } else {
-                          valsList.push(decl);
-                      }
+            name += "]";
+            // name += is_mutable;
+            name += exprName(arrayObj.child, opts);
+            return name;
+          }
+          case typeKinds.Optional:
+            return "?" + exprName(typeObj.child, opts);
+          case typeKinds.Pointer: {
+            let ptrObj = typeObj;
+            let sentinel = ptrObj.sentinel
+              ? ":" + exprName(ptrObj.sentinel, opts)
+              : "";
+            let is_mutable = !ptrObj.is_mutable ? "const " : "";
+            let name = "";
+            switch (ptrObj.size) {
+              default:
+                console.log("TODO: implement unhandled pointer size case");
+              case pointerSizeEnum.One:
+                name += "*";
+                name += is_mutable;
+                break;
+              case pointerSizeEnum.Many:
+                name += "[*";
+                name += sentinel;
+                name += "]";
+                name += is_mutable;
+                break;
+              case pointerSizeEnum.Slice:
+                if (ptrObj.is_ref) {
+                  name += "*";
+                }
+                name += "[";
+                name += sentinel;
+                name += "]";
+                name += is_mutable;
+                break;
+              case pointerSizeEnum.C:
+                name += "[*c";
+                name += sentinel;
+                name += "]";
+                name += is_mutable;
+                break;
+            }
+            // @check: after the major changes in arrays the consts are came from switch above
+            // if (!ptrObj.is_mutable) {
+            //     if (opts.wantHtml) {
+            //         name += '<span class="tok-kw">const</span> ';
+            //     } else {
+            //         name += "const ";
+            //     }
+            // }
+            if (ptrObj.is_allowzero) {
+              name += "allowzero ";
+            }
+            if (ptrObj.is_volatile) {
+              name += "volatile ";
+            }
+            if (ptrObj.has_addrspace) {
+              name += "addrspace(";
+              name += "." + "";
+              name += ") ";
+            }
+            if (ptrObj.has_align) {
+              let align = exprName(ptrObj.align, opts);
+              if (opts.wantHtml) {
+                name += '<span class="tok-kw">align</span>(';
+              } else {
+                name += "align(";
+              }
+              if (opts.wantHtml) {
+                name += '<span class="tok-number">' + align + "</span>";
+              } else {
+                name += align;
+              }
+              if (ptrObj.hostIntBytes != null) {
+                name += ":";
+                if (opts.wantHtml) {
+                  name +=
+                    '<span class="tok-number">' +
+                    ptrObj.bitOffsetInHost +
+                    "</span>";
                 } else {
-                    valsList.push(decl);
+                  name += ptrObj.bitOffsetInHost;
                 }
+                name += ":";
+                if (opts.wantHtml) {
+                  name +=
+                    '<span class="tok-number">' +
+                    ptrObj.hostIntBytes +
+                    "</span>";
+                } else {
+                  name += ptrObj.hostIntBytes;
+                }
+              }
+              name += ") ";
             }
-        }
-    }
+            //name += typeValueName(ptrObj.child, wantHtml, wantSubLink, null);
+            name += exprName(ptrObj.child, opts);
+            return name;
+          }
+          case typeKinds.Float: {
+            let floatObj = typeObj;
 
-    
-    function renderContainer(container) {
-        
-        let typesList = [];
-        
-        let namespacesList = [];
-        
-        let errSetsList = [];
-        
-        let fnsList = [];
-        
-        let varsList = [];
-        
-        let valsList = [];
-        
-        let testsList = [];
-
-        categorizeDecls(container.pubDecls,
-            typesList, namespacesList, errSetsList,
-            fnsList, varsList, valsList, testsList);
-        if (curNav.showPrivDecls) categorizeDecls(container.privDecls,
-            typesList, namespacesList, errSetsList,
-            fnsList, varsList, valsList, testsList);
-
-
-        typesList.sort(byNameProperty);
-        namespacesList.sort(byNameProperty);
-        errSetsList.sort(byNameProperty);
-        fnsList.sort(byNameProperty);
-        varsList.sort(byNameProperty);
-        valsList.sort(byNameProperty);
-        testsList.sort(byNameProperty);
-
-        if (container.src != null) {
-            let docs = zigAnalysis.astNodes[container.src].docs;
-            if (docs != null) {
-                domTldDocs.innerHTML = markdown(docs);
-                domTldDocs.classList.remove("hidden");
+            if (opts.wantHtml) {
+              return '<span class="tok-type">' + floatObj.name + "</span>";
+            } else {
+              return floatObj.name;
             }
-        }
-
-        if (typesList.length !== 0) {
-            window.x = typesList;
-            resizeDomList(domListTypes, typesList.length, '<li><a href="#"></a></li>');
-            for (let i = 0; i < typesList.length; i += 1) {
-                let liDom = domListTypes.children[i];
-                let aDom = liDom.children[0];
-                let decl = typesList[i];
-                aDom.textContent = decl.name;
-                aDom.setAttribute('href', navLinkDecl(decl.name));
+          }
+          case typeKinds.Int: {
+            let intObj = typeObj;
+            let name = intObj.name;
+            if (opts.wantHtml) {
+              return '<span class="tok-type">' + name + "</span>";
+            } else {
+              return name;
             }
-            domSectTypes.classList.remove("hidden");
-        }
-        if (namespacesList.length !== 0) {
-            resizeDomList(domListNamespaces, namespacesList.length, '<li><a href="#"></a></li>');
-            for (let i = 0; i < namespacesList.length; i += 1) {
-                let liDom = domListNamespaces.children[i];
-                let aDom = liDom.children[0];
-                let decl = namespacesList[i];
-                aDom.textContent = decl.name;
-                aDom.setAttribute('href', navLinkDecl(decl.name));
+          }
+          case typeKinds.ComptimeInt:
+            if (opts.wantHtml) {
+              return '<span class="tok-type">comptime_int</span>';
+            } else {
+              return "comptime_int";
             }
-            domSectNamespaces.classList.remove("hidden");
-        }
-
-        if (errSetsList.length !== 0) {
-            resizeDomList(domListErrSets, errSetsList.length, '<li><a href="#"></a></li>');
-            for (let i = 0; i < errSetsList.length; i += 1) {
-                let liDom = domListErrSets.children[i];
-                let aDom = liDom.children[0];
-                let decl = errSetsList[i];
-                aDom.textContent = decl.name;
-                aDom.setAttribute('href', navLinkDecl(decl.name));
+          case typeKinds.ComptimeFloat:
+            if (opts.wantHtml) {
+              return '<span class="tok-type">comptime_float</span>';
+            } else {
+              return "comptime_float";
             }
-            domSectErrSets.classList.remove("hidden");
-        }
-
-        if (fnsList.length !== 0) {
-            resizeDomList(domListFns, fnsList.length, '<div><dt></dt><dd></dd></div>');
-
-            for (let i = 0; i < fnsList.length; i += 1) {
-                let decl = fnsList[i];
-                let trDom = domListFns.children[i];
-
-                let tdFnCode = trDom.children[0];
-                let tdDesc = trDom.children[1];
-
-                let declType = resolveValue(decl.value);
-                console.assert("type" in declType.expr);
-
-                tdFnCode.innerHTML = exprName(declType.expr,{
-                  wantHtml: true,
-                  wantLink: true,
-                  fnDecl: decl,
-                  linkFnNameDecl: navLinkDecl(decl.name),
-                });
+          case typeKinds.Type:
+            if (opts.wantHtml) {
+              return '<span class="tok-type">type</span>';
+            } else {
+              return "type";
+            }
+          case typeKinds.Bool:
+            if (opts.wantHtml) {
+              return '<span class="tok-type">bool</span>';
+            } else {
+              return "bool";
+            }
+          case typeKinds.Void:
+            if (opts.wantHtml) {
+              return '<span class="tok-type">void</span>';
+            } else {
+              return "void";
+            }
+          case typeKinds.EnumLiteral:
+            if (opts.wantHtml) {
+              return '<span class="tok-type">(enum literal)</span>';
+            } else {
+              return "(enum literal)";
+            }
+          case typeKinds.NoReturn:
+            if (opts.wantHtml) {
+              return '<span class="tok-type">noreturn</span>';
+            } else {
+              return "noreturn";
+            }
+          case typeKinds.ErrorSet: {
+            let errSetObj = typeObj;
+            if (errSetObj.fields == null) {
+              return '<span class="tok-type">anyerror</span>';
+            } else {
+              // throw "TODO";
+              let html = "error{" + errSetObj.fields[0].name + "}";
+              return html;
+            }
+          }
 
-                let docs = zigAnalysis.astNodes[decl.src].docs;
-                if (docs != null) {
-                    tdDesc.innerHTML = shortDescMarkdown(docs);
+          case typeKinds.ErrorUnion: {
+            let errUnionObj = typeObj;
+            let lhs = exprName(errUnionObj.lhs, opts);
+            let rhs = exprName(errUnionObj.rhs, opts);
+            return lhs + "!" + rhs;
+          }
+          case typeKinds.InferredErrorUnion: {
+            let errUnionObj = typeObj;
+            let payload = exprName(errUnionObj.payload, opts);
+            return "!" + payload;
+          }
+          case typeKinds.Fn: {
+            let fnObj = typeObj;
+            let payloadHtml = "";
+            if (opts.wantHtml) {
+              if (fnObj.is_extern) {
+                payloadHtml += "pub extern ";
+              }
+              if (fnObj.has_lib_name) {
+                payloadHtml += '"' + fnObj.lib_name + '" ';
+              }
+              payloadHtml += '<span class="tok-kw">fn</span>';
+              if (opts.fnDecl) {
+                payloadHtml += ' <span class="tok-fn">';
+                if (opts.linkFnNameDecl) {
+                  payloadHtml +=
+                    '<a href="' +
+                    opts.linkFnNameDecl +
+                    '">' +
+                    escapeHtml(opts.fnDecl.name) +
+                    "</a>";
                 } else {
-                    tdDesc.textContent = "";
+                  payloadHtml += escapeHtml(opts.fnDecl.name);
                 }
-            }
-            domSectFns.classList.remove("hidden");
-        }
+                payloadHtml += "</span>";
+              }
+            } else {
+              payloadHtml += "fn ";
+            }
+            payloadHtml += "(";
+            if (fnObj.params) {
+              let fields = null;
+              let isVarArgs = false;
+              let fnNode = zigAnalysis.astNodes[fnObj.src];
+              fields = fnNode.fields;
+              isVarArgs = fnNode.varArgs;
+
+              for (let i = 0; i < fnObj.params.length; i += 1) {
+                if (i != 0) {
+                  payloadHtml += ", ";
+                }
+
+                payloadHtml +=
+                  "<span class='argBreaker'><br>&nbsp;&nbsp;&nbsp;&nbsp;</span>";
+                let value = fnObj.params[i];
+                let paramValue = resolveValue({ expr: value });
 
-        let containerNode = zigAnalysis.astNodes[container.src];
-        if (containerNode.fields && containerNode.fields.length > 0) {
-            resizeDomList(domListFields, containerNode.fields.length, '<div></div>');
+                if (fields != null) {
+                  let paramNode = zigAnalysis.astNodes[fields[i]];
 
-            for (let i = 0; i < containerNode.fields.length; i += 1) {
-                let fieldNode = zigAnalysis.astNodes[containerNode.fields[i]];
-                let divDom = domListFields.children[i];
-                let fieldName = (fieldNode.name);
-                let docs = fieldNode.docs;
-                let docsNonEmpty = docs != null && docs !== "";
-                let extraPreClass = docsNonEmpty ? " fieldHasDocs" : "";
+                  if (paramNode.varArgs) {
+                    payloadHtml += "...";
+                    continue;
+                  }
 
-                let html = '<div class="mobile-scroll-container"><pre class="scroll-item' + extraPreClass + '">' + escapeHtml(fieldName);
+                  if (paramNode.noalias) {
+                    if (opts.wantHtml) {
+                      payloadHtml += '<span class="tok-kw">noalias</span> ';
+                    } else {
+                      payloadHtml += "noalias ";
+                    }
+                  }
 
-                if (container.kind === typeKinds.Enum) {
-                    html += ' = <span class="tok-number">' + fieldName + '</span>';
-                } else {
-                    let fieldTypeExpr = container.fields[i];
-                    html += ": ";
-                    let name = exprName(fieldTypeExpr, false, false);
-                    html += '<span class="tok-kw">'+ name +'</span>';
-                    let tsn = typeShorthandName(fieldTypeExpr);
-                    if (tsn) {
-                        html += '<span> ('+ tsn +')</span>';
+                  if (paramNode.comptime) {
+                    if (opts.wantHtml) {
+                      payloadHtml += '<span class="tok-kw">comptime</span> ';
+                    } else {
+                      payloadHtml += "comptime ";
+                    }
+                  }
 
+                  let paramName = paramNode.name;
+                  if (paramName != null) {
+                    // skip if it matches the type name
+                    if (!shouldSkipParamName(paramValue, paramName)) {
+                      payloadHtml += paramName + ": ";
                     }
+                  }
                 }
 
-                html += ',</pre></div>';
-
-                if (docsNonEmpty) {
-                    html += '<div class="fieldDocs">' + markdown(docs) + '</div>';
+                if (isVarArgs && i === fnObj.params.length - 1) {
+                  payloadHtml += "...";
+                } else if ("alignOf" in value) {
+                  if (opts.wantHtml) {
+                    payloadHtml += '<a href="">';
+                    payloadHtml +=
+                      '<span class="tok-kw" style="color:lightblue;">' +
+                      exprName(value, opts) +
+                      "</span>";
+                    payloadHtml += "</a>";
+                  } else {
+                    payloadHtml += exprName(value, opts);
+                  }
+                } else if ("typeOf" in value) {
+                  if (opts.wantHtml) {
+                    payloadHtml += '<a href="">';
+                    payloadHtml +=
+                      '<span class="tok-kw" style="color:lightblue;">' +
+                      exprName(value, opts) +
+                      "</span>";
+                    payloadHtml += "</a>";
+                  } else {
+                    payloadHtml += exprName(value, opts);
+                  }
+                } else if ("typeOf_peer" in value) {
+                  if (opts.wantHtml) {
+                    payloadHtml += '<a href="">';
+                    payloadHtml +=
+                      '<span class="tok-kw" style="color:lightblue;">' +
+                      exprName(value, opts) +
+                      "</span>";
+                    payloadHtml += "</a>";
+                  } else {
+                    payloadHtml += exprName(value, opts);
+                  }
+                } else if ("declRef" in value) {
+                  if (opts.wantHtml) {
+                    payloadHtml += '<a href="">';
+                    payloadHtml +=
+                      '<span class="tok-kw" style="color:lightblue;">' +
+                      exprName(value, opts) +
+                      "</span>";
+                    payloadHtml += "</a>";
+                  } else {
+                    payloadHtml += exprName(value, opts);
+                  }
+                } else if ("call" in value) {
+                  if (opts.wantHtml) {
+                    payloadHtml += '<a href="">';
+                    payloadHtml +=
+                      '<span class="tok-kw" style="color:lightblue;">' +
+                      exprName(value, opts) +
+                      "</span>";
+                    payloadHtml += "</a>";
+                  } else {
+                    payloadHtml += exprName(value, opts);
+                  }
+                } else if ("refPath" in value) {
+                  if (opts.wantHtml) {
+                    payloadHtml += '<a href="">';
+                    payloadHtml +=
+                      '<span class="tok-kw" style="color:lightblue;">' +
+                      exprName(value, opts) +
+                      "</span>";
+                    payloadHtml += "</a>";
+                  } else {
+                    payloadHtml += exprName(value, opts);
+                  }
+                } else if ("type" in value) {
+                  let name = exprName(value, {
+                    wantHtml: false,
+                    wantLink: false,
+                    fnDecl: opts.fnDecl,
+                    linkFnNameDecl: opts.linkFnNameDecl,
+                  });
+                  payloadHtml += '<span class="tok-kw">' + name + "</span>";
+                } else if ("binOpIndex" in value) {
+                  payloadHtml += exprName(value, opts);
+                } else if ("comptimeExpr" in value) {
+                  let comptimeExpr =
+                    zigAnalysis.comptimeExprs[value.comptimeExpr].code;
+                  if (opts.wantHtml) {
+                    payloadHtml +=
+                      '<span class="tok-kw">' + comptimeExpr + "</span>";
+                  } else {
+                    payloadHtml += comptimeExpr;
+                  }
+                } else if (opts.wantHtml) {
+                  payloadHtml += '<span class="tok-kw">anytype</span>';
+                } else {
+                  payloadHtml += "anytype";
                 }
-                divDom.innerHTML = html;
+              }
             }
-            domSectFields.classList.remove("hidden");
-        }
-
-        if (varsList.length !== 0) {
-            resizeDomList(domListGlobalVars, varsList.length,
-                '<tr><td><a href="#"></a></td><td></td><td></td></tr>');
-            for (let i = 0; i < varsList.length; i += 1) {
-                let decl = varsList[i];
-                let trDom = domListGlobalVars.children[i];
 
-                let tdName = trDom.children[0];
-                let tdNameA = tdName.children[0];
-                let tdType = trDom.children[1];
-                let tdDesc = trDom.children[2];
+            payloadHtml += "<span class='argBreaker'>,<br></span>";
+            payloadHtml += ") ";
 
-                tdNameA.setAttribute('href', navLinkDecl(decl.name));
-                tdNameA.textContent = decl.name;
-
-                tdType.innerHTML = typeValueName(typeOfDecl(decl), true, true);
+            if (fnObj.has_align) {
+              let align = zigAnalysis.exprs[fnObj.align];
+              payloadHtml += "align(" + exprName(align, opts) + ") ";
+            }
+            if (fnObj.has_cc) {
+              let cc = zigAnalysis.exprs[fnObj.cc];
+              if (cc) {
+                payloadHtml += "callconv(." + cc.enumLiteral + ") ";
+              }
+            }
 
-                let docs = zigAnalysis.astNodes[decl.src].docs;
-                if (docs != null) {
-                    tdDesc.innerHTML = shortDescMarkdown(docs);
-                } else {
-                    tdDesc.textContent = "";
-                }
+            if (fnObj.is_inferred_error) {
+              payloadHtml += "!";
+            }
+            if (fnObj.ret != null) {
+              payloadHtml += exprName(fnObj.ret, opts);
+            } else if (opts.wantHtml) {
+              payloadHtml += '<span class="tok-kw">anytype</span>';
+            } else {
+              payloadHtml += "anytype";
             }
-            domSectGlobalVars.classList.remove("hidden");
+            return payloadHtml;
+          }
+          // if (wantHtml) {
+          //     return escapeHtml(typeObj.name);
+          // } else {
+          //     return typeObj.name;
+          // }
+        }
+      }
+    }
+  }
+
+  function shouldSkipParamName(typeRef, paramName) {
+    let resolvedTypeRef = resolveValue({ expr: typeRef });
+    if ("type" in resolvedTypeRef) {
+      let typeObj = zigAnalysis.types[resolvedTypeRef.type];
+      if (typeObj.kind === typeKinds.Pointer) {
+        let ptrObj = typeObj;
+        if (getPtrSize(ptrObj) === pointerSizeEnum.One) {
+          const value = resolveValue(ptrObj.child);
+          return typeValueName(value, false, true).toLowerCase() === paramName;
         }
+      }
+    }
+    return false;
+  }
+
+  function getPtrSize(typeObj) {
+    return typeObj.size == null ? pointerSizeEnum.One : typeObj.size;
+  }
+
+  function renderType(typeObj) {
+    let name;
+    if (
+      rootIsStd &&
+      typeObj ===
+        zigAnalysis.types[zigAnalysis.packages[zigAnalysis.rootPkg].main]
+    ) {
+      name = "std";
+    } else {
+      name = exprName({ type: typeObj }, false, false);
+    }
+    if (name != null && name != "") {
+      domHdrName.innerText =
+        name + " (" + zigAnalysis.typeKinds[typeObj.kind] + ")";
+      domHdrName.classList.remove("hidden");
+    }
+    if (typeObj.kind == typeKinds.ErrorSet) {
+      renderErrorSet(typeObj);
+    }
+  }
 
-        if (valsList.length !== 0) {
-            resizeDomList(domListValues, valsList.length,
-                '<tr><td><a href="#"></a></td><td></td><td></td></tr>');
-            for (let i = 0; i < valsList.length; i += 1) {
-                let decl = valsList[i];
-                let trDom = domListValues.children[i];
+  function renderErrorSet(errSetType) {
+    if (errSetType.fields == null) {
+      domFnErrorsAnyError.classList.remove("hidden");
+    } else {
+      let errorList = [];
+      for (let i = 0; i < errSetType.fields.length; i += 1) {
+        let errObj = errSetType.fields[i];
+        //let srcObj = zigAnalysis.astNodes[errObj.src];
+        errorList.push(errObj);
+      }
+      errorList.sort(function (a, b) {
+        return operatorCompare(a.name.toLowerCase(), b.name.toLowerCase());
+      });
+
+      resizeDomListDl(domListFnErrors, errorList.length);
+      for (let i = 0; i < errorList.length; i += 1) {
+        let nameTdDom = domListFnErrors.children[i * 2 + 0];
+        let descTdDom = domListFnErrors.children[i * 2 + 1];
+        nameTdDom.textContent = errorList[i].name;
+        let docs = errorList[i].docs;
+        if (docs != null) {
+          descTdDom.innerHTML = markdown(docs);
+        } else {
+          descTdDom.textContent = "";
+        }
+      }
+      domTableFnErrors.classList.remove("hidden");
+    }
+    domSectFnErrors.classList.remove("hidden");
+  }
+
+  //     function allCompTimeFnCallsHaveTypeResult(typeIndex, value) {
+  //         let srcIndex = zigAnalysis.fns[value].src;
+  //         let calls = nodesToCallsMap[srcIndex];
+  //         if (calls == null) return false;
+  //         for (let i = 0; i < calls.length; i += 1) {
+  //             let call = zigAnalysis.calls[calls[i]];
+  //             if (call.result.type !== typeTypeId) return false;
+  //         }
+  //         return true;
+  //     }
+  //
+  //     function allCompTimeFnCallsResult(calls) {
+  //         let firstTypeObj = null;
+  //         let containerObj = {
+  //             privDecls: [],
+  //         };
+  //         for (let callI = 0; callI < calls.length; callI += 1) {
+  //             let call = zigAnalysis.calls[calls[callI]];
+  //             if (call.result.type !== typeTypeId) return null;
+  //             let typeObj = zigAnalysis.types[call.result.value];
+  //             if (!typeKindIsContainer(typeObj.kind)) return null;
+  //             if (firstTypeObj == null) {
+  //                 firstTypeObj = typeObj;
+  //                 containerObj.src = typeObj.src;
+  //             } else if (firstTypeObj.src !== typeObj.src) {
+  //                 return null;
+  //             }
+  //
+  //             if (containerObj.fields == null) {
+  //                 containerObj.fields = (typeObj.fields || []).concat([]);
+  //             } else for (let fieldI = 0; fieldI < typeObj.fields.length; fieldI += 1) {
+  //                 let prev = containerObj.fields[fieldI];
+  //                 let next = typeObj.fields[fieldI];
+  //                 if (prev === next) continue;
+  //                 if (typeof(prev) === 'object') {
+  //                     if (prev[next] == null) prev[next] = typeObj;
+  //                 } else {
+  //                     containerObj.fields[fieldI] = {};
+  //                     containerObj.fields[fieldI][prev] = firstTypeObj;
+  //                     containerObj.fields[fieldI][next] = typeObj;
+  //                 }
+  //             }
+  //
+  //             if (containerObj.pubDecls == null) {
+  //                 containerObj.pubDecls = (typeObj.pubDecls || []).concat([]);
+  //             } else for (let declI = 0; declI < typeObj.pubDecls.length; declI += 1) {
+  //                 let prev = containerObj.pubDecls[declI];
+  //                 let next = typeObj.pubDecls[declI];
+  //                 if (prev === next) continue;
+  //                 // TODO instead of showing "examples" as the public declarations,
+  //                     // do logic like this:
+  //                 //if (typeof(prev) !== 'object') {
+  //                     //    let newDeclId = zigAnalysis.decls.length;
+  //                     //    prev = clone(zigAnalysis.decls[prev]);
+  //                     //    prev.id = newDeclId;
+  //                     //    zigAnalysis.decls.push(prev);
+  //                     //    containerObj.pubDecls[declI] = prev;
+  //                     //}
+  //                 //mergeDecls(prev, next, firstTypeObj, typeObj);
+  //             }
+  //         }
+  //         for (let declI = 0; declI < containerObj.pubDecls.length; declI += 1) {
+  //             let decl = containerObj.pubDecls[declI];
+  //             if (typeof(decl) === 'object') {
+  //                 containerObj.pubDecls[declI] = containerObj.pubDecls[declI].id;
+  //             }
+  //         }
+  //         return containerObj;
+  //     }
+
+  function renderValue(decl) {
+    let resolvedValue = resolveValue(decl.value);
+
+    if (resolvedValue.expr.fieldRef) {
+      const declRef = decl.value.expr.refPath[0].declRef;
+      const type = zigAnalysis.decls[declRef];
+      domFnProtoCode.innerHTML =
+        '<span class="tok-kw">const</span> ' +
+        escapeHtml(decl.name) +
+        ": " +
+        type.name +
+        " = " +
+        exprName(decl.value.expr, { wantHtml: true, wantLink: true }) +
+        ";";
+    } else if (
+      resolvedValue.expr.string !== undefined ||
+      resolvedValue.expr.call !== undefined ||
+      resolvedValue.expr.comptimeExpr
+    ) {
+      domFnProtoCode.innerHTML =
+        '<span class="tok-kw">const</span> ' +
+        escapeHtml(decl.name) +
+        ": " +
+        exprName(resolvedValue.expr, { wantHtml: true, wantLink: true }) +
+        " = " +
+        exprName(decl.value.expr, { wantHtml: true, wantLink: true }) +
+        ";";
+    } else if (resolvedValue.expr.compileError) {
+      domFnProtoCode.innerHTML =
+        '<span class="tok-kw">const</span> ' +
+        escapeHtml(decl.name) +
+        " = " +
+        exprName(decl.value.expr, { wantHtml: true, wantLink: true }) +
+        ";";
+    } else {
+      domFnProtoCode.innerHTML =
+        '<span class="tok-kw">const</span> ' +
+        escapeHtml(decl.name) +
+        ": " +
+        exprName(resolvedValue.typeRef, { wantHtml: true, wantLink: true }) +
+        " = " +
+        exprName(decl.value.expr, { wantHtml: true, wantLink: true }) +
+        ";";
+    }
 
-                let tdName = trDom.children[0];
-                let tdNameA = tdName.children[0];
-                let tdType = trDom.children[1];
-                let tdDesc = trDom.children[2];
+    let docs = zigAnalysis.astNodes[decl.src].docs;
+    if (docs != null) {
+      domTldDocs.innerHTML = markdown(docs);
+      domTldDocs.classList.remove("hidden");
+    }
 
-                tdNameA.setAttribute('href', navLinkDecl(decl.name));
-                tdNameA.textContent = decl.name;
+    domFnProto.classList.remove("hidden");
+  }
+
+  function renderVar(decl) {
+    let declTypeRef = typeOfDecl(decl);
+    domFnProtoCode.innerHTML =
+      '<span class="tok-kw">var</span> ' +
+      escapeHtml(decl.name) +
+      ": " +
+      typeValueName(declTypeRef, true, true);
+
+    let docs = zigAnalysis.astNodes[decl.src].docs;
+    if (docs != null) {
+      domTldDocs.innerHTML = markdown(docs);
+      domTldDocs.classList.remove("hidden");
+    }
 
-                tdType.innerHTML = exprName(walkResultTypeRef(decl.value),
-                  {wantHtml:true, wantLink:true});
+    domFnProto.classList.remove("hidden");
+  }
+
+  function categorizeDecls(
+    decls,
+    typesList,
+    namespacesList,
+    errSetsList,
+    fnsList,
+    varsList,
+    valsList,
+    testsList
+  ) {
+    for (let i = 0; i < decls.length; i += 1) {
+      let decl = zigAnalysis.decls[decls[i]];
+      let declValue = resolveValue(decl.value);
+
+      if (decl.isTest) {
+        testsList.push(decl);
+        continue;
+      }
 
-                let docs = zigAnalysis.astNodes[decl.src].docs;
-                if (docs != null) {
-                    tdDesc.innerHTML = shortDescMarkdown(docs);
-                } else {
-                    tdDesc.textContent = "";
-                }
+      if (decl.kind === "var") {
+        varsList.push(decl);
+        continue;
+      }
+
+      if (decl.kind === "const") {
+        if ("type" in declValue.expr) {
+          // We have the actual type expression at hand.
+          const typeExpr = zigAnalysis.types[declValue.expr.type];
+          if (typeExpr.kind == typeKinds.Fn) {
+            const funcRetExpr = resolveValue({
+              expr: typeExpr.ret,
+            });
+            if (
+              "type" in funcRetExpr.expr &&
+              funcRetExpr.expr.type == typeTypeId
+            ) {
+              if (typeIsErrSet(declValue.expr.type)) {
+                errSetsList.push(decl);
+              } else if (typeIsStructWithNoFields(declValue.expr.type)) {
+                namespacesList.push(decl);
+              } else {
+                typesList.push(decl);
+              }
+            } else {
+              fnsList.push(decl);
+            }
+          } else {
+            if (typeIsErrSet(declValue.expr.type)) {
+              errSetsList.push(decl);
+            } else if (typeIsStructWithNoFields(declValue.expr.type)) {
+              namespacesList.push(decl);
+            } else {
+              typesList.push(decl);
             }
-            domSectValues.classList.remove("hidden");
+          }
+        } else if ("typeRef" in declValue) {
+          if ("type" in declValue.typeRef && declValue.typeRef == typeTypeId) {
+            // We don't know what the type expression is, but we know it's a type.
+            typesList.push(decl);
+          } else {
+            valsList.push(decl);
+          }
+        } else {
+          valsList.push(decl);
         }
+      }
+    }
+  }
+
+  function renderContainer(container) {
+    let typesList = [];
+
+    let namespacesList = [];
+
+    let errSetsList = [];
+
+    let fnsList = [];
+
+    let varsList = [];
+
+    let valsList = [];
+
+    let testsList = [];
+
+    categorizeDecls(
+      container.pubDecls,
+      typesList,
+      namespacesList,
+      errSetsList,
+      fnsList,
+      varsList,
+      valsList,
+      testsList
+    );
+    if (curNav.showPrivDecls)
+      categorizeDecls(
+        container.privDecls,
+        typesList,
+        namespacesList,
+        errSetsList,
+        fnsList,
+        varsList,
+        valsList,
+        testsList
+      );
+
+    typesList.sort(byNameProperty);
+    namespacesList.sort(byNameProperty);
+    errSetsList.sort(byNameProperty);
+    fnsList.sort(byNameProperty);
+    varsList.sort(byNameProperty);
+    valsList.sort(byNameProperty);
+    testsList.sort(byNameProperty);
+
+    if (container.src != null) {
+      let docs = zigAnalysis.astNodes[container.src].docs;
+      if (docs != null) {
+        domTldDocs.innerHTML = markdown(docs);
+        domTldDocs.classList.remove("hidden");
+      }
+    }
 
-        if (testsList.length !== 0) {
-            resizeDomList(domListTests, testsList.length,
-                '<tr><td><a href="#"></a></td><td></td><td></td></tr>');
-            for (let i = 0; i < testsList.length; i += 1) {
-                let decl = testsList[i];
-                let trDom = domListTests.children[i];
-
-                let tdName = trDom.children[0];
-                let tdNameA = tdName.children[0];
-                let tdType = trDom.children[1];
-                let tdDesc = trDom.children[2];
+    if (typesList.length !== 0) {
+      window.x = typesList;
+      resizeDomList(
+        domListTypes,
+        typesList.length,
+        '<li><a href="#"></a></li>'
+      );
+      for (let i = 0; i < typesList.length; i += 1) {
+        let liDom = domListTypes.children[i];
+        let aDom = liDom.children[0];
+        let decl = typesList[i];
+        aDom.textContent = decl.name;
+        aDom.setAttribute("href", navLinkDecl(decl.name));
+      }
+      domSectTypes.classList.remove("hidden");
+    }
+    if (namespacesList.length !== 0) {
+      resizeDomList(
+        domListNamespaces,
+        namespacesList.length,
+        '<li><a href="#"></a></li>'
+      );
+      for (let i = 0; i < namespacesList.length; i += 1) {
+        let liDom = domListNamespaces.children[i];
+        let aDom = liDom.children[0];
+        let decl = namespacesList[i];
+        aDom.textContent = decl.name;
+        aDom.setAttribute("href", navLinkDecl(decl.name));
+      }
+      domSectNamespaces.classList.remove("hidden");
+    }
 
-                tdNameA.setAttribute('href', navLinkDecl(decl.name));
-                tdNameA.textContent = decl.name;
+    if (errSetsList.length !== 0) {
+      resizeDomList(
+        domListErrSets,
+        errSetsList.length,
+        '<li><a href="#"></a></li>'
+      );
+      for (let i = 0; i < errSetsList.length; i += 1) {
+        let liDom = domListErrSets.children[i];
+        let aDom = liDom.children[0];
+        let decl = errSetsList[i];
+        aDom.textContent = decl.name;
+        aDom.setAttribute("href", navLinkDecl(decl.name));
+      }
+      domSectErrSets.classList.remove("hidden");
+    }
 
-                tdType.innerHTML = exprName(walkResultTypeRef(decl.value),
-                  {wantHtml:true, wantLink:true});
+    if (fnsList.length !== 0) {
+      resizeDomList(
+        domListFns,
+        fnsList.length,
+        "<div><dt></dt><dd></dd></div>"
+      );
 
-                let docs = zigAnalysis.astNodes[decl.src].docs;
-                if (docs != null) {
-                    tdDesc.innerHTML = shortDescMarkdown(docs);
-                } else {
-                    tdDesc.textContent = "";
-                }
-            }
-            domSectTests.classList.remove("hidden");
-        }
-    }
+      for (let i = 0; i < fnsList.length; i += 1) {
+        let decl = fnsList[i];
+        let trDom = domListFns.children[i];
 
+        let tdFnCode = trDom.children[0];
+        let tdDesc = trDom.children[1];
 
-    
-    function operatorCompare(a, b) {
-        if (a === b) {
-            return 0;
-        } else if (a < b) {
-            return -1;
+        let declType = resolveValue(decl.value);
+        console.assert("type" in declType.expr);
+
+        tdFnCode.innerHTML = exprName(declType.expr, {
+          wantHtml: true,
+          wantLink: true,
+          fnDecl: decl,
+          linkFnNameDecl: navLinkDecl(decl.name),
+        });
+
+        let docs = zigAnalysis.astNodes[decl.src].docs;
+        if (docs != null) {
+          tdDesc.innerHTML = shortDescMarkdown(docs);
         } else {
-            return 1;
+          tdDesc.textContent = "";
         }
+      }
+      domSectFns.classList.remove("hidden");
     }
 
-    function detectRootIsStd() {
-        let rootPkg = zigAnalysis.packages[zigAnalysis.rootPkg];
-        if (rootPkg.table["std"] == null) {
-            // no std mapped into the root package
-            return false;
+    let containerNode = zigAnalysis.astNodes[container.src];
+    if (containerNode.fields && containerNode.fields.length > 0) {
+      resizeDomList(domListFields, containerNode.fields.length, "<div></div>");
+
+      for (let i = 0; i < containerNode.fields.length; i += 1) {
+        let fieldNode = zigAnalysis.astNodes[containerNode.fields[i]];
+        let divDom = domListFields.children[i];
+        let fieldName = fieldNode.name;
+        let docs = fieldNode.docs;
+        let docsNonEmpty = docs != null && docs !== "";
+        let extraPreClass = docsNonEmpty ? " fieldHasDocs" : "";
+
+        let html =
+          '<div class="mobile-scroll-container"><pre class="scroll-item' +
+          extraPreClass +
+          '">' +
+          escapeHtml(fieldName);
+
+        if (container.kind === typeKinds.Enum) {
+          html += ' = <span class="tok-number">' + fieldName + "</span>";
+        } else {
+          let fieldTypeExpr = container.fields[i];
+          html += ": ";
+          let name = exprName(fieldTypeExpr, false, false);
+          html += '<span class="tok-kw">' + name + "</span>";
+          let tsn = typeShorthandName(fieldTypeExpr);
+          if (tsn) {
+            html += "<span> (" + tsn + ")</span>";
+          }
         }
-        let stdPkg = zigAnalysis.packages[rootPkg.table["std"]];
-        if (stdPkg == null) return false;
-        return rootPkg.file === stdPkg.file;
-    }
 
-    function indexTypeKinds() {
-        let map = ({});
-        for (let i = 0; i < zigAnalysis.typeKinds.length; i += 1) {
-            map[zigAnalysis.typeKinds[i]] = i;
-        }
-        // This is just for debugging purposes, not needed to function
-        let assertList = ["Type","Void","Bool","NoReturn","Int","Float","Pointer","Array","Struct",
-            "ComptimeFloat","ComptimeInt","Undefined","Null","Optional","ErrorUnion","ErrorSet","Enum",
-            "Union","Fn","BoundFn","Opaque","Frame","AnyFrame","Vector","EnumLiteral"];
-        for (let i = 0; i < assertList.length; i += 1) {
-            if (map[assertList[i]] == null) throw new Error("No type kind '" + assertList[i] + "' found");
-        }
-        return map;
-    }
+        html += ",</pre></div>";
 
-    function findTypeTypeId() {
-        for (let i = 0; i < zigAnalysis.types.length; i += 1) {
-            if (zigAnalysis.types[i].kind == typeKinds.Type) {
-                return i;
-            }
+        if (docsNonEmpty) {
+          html += '<div class="fieldDocs">' + markdown(docs) + "</div>";
         }
-        throw new Error("No type 'type' found");
+        divDom.innerHTML = html;
+      }
+      domSectFields.classList.remove("hidden");
     }
 
-    function updateCurNav() {
+    if (varsList.length !== 0) {
+      resizeDomList(
+        domListGlobalVars,
+        varsList.length,
+        '<tr><td><a href="#"></a></td><td></td><td></td></tr>'
+      );
+      for (let i = 0; i < varsList.length; i += 1) {
+        let decl = varsList[i];
+        let trDom = domListGlobalVars.children[i];
 
-        curNav = {
-            showPrivDecls: false,
-            pkgNames: [],
-            pkgObjs: [],
-            declNames: [],
-            declObjs: [],
-            callName: null,
-        };
-        curNavSearch = "";
+        let tdName = trDom.children[0];
+        let tdNameA = tdName.children[0];
+        let tdType = trDom.children[1];
+        let tdDesc = trDom.children[2];
 
-        if (location.hash[0] === '#' && location.hash.length > 1) {
-            let query = location.hash.substring(1);
-            if (query[0] === '*') {
-              curNav.showPrivDecls = true;
-              query = query.substring(1);
-            }
+        tdNameA.setAttribute("href", navLinkDecl(decl.name));
+        tdNameA.textContent = decl.name;
 
-            let qpos = query.indexOf("?");
-            let nonSearchPart;
-            if (qpos === -1) {
-                nonSearchPart = query;
-            } else {
-                nonSearchPart = query.substring(0, qpos);
-                curNavSearch = decodeURIComponent(query.substring(qpos + 1));
-            }
+        tdType.innerHTML = typeValueName(typeOfDecl(decl), true, true);
 
-            let parts = nonSearchPart.split(";");
-            curNav.pkgNames = decodeURIComponent(parts[0]).split(".");
-            if (parts[1] != null) {
-                curNav.declNames = decodeURIComponent(parts[1]).split(".");
-            }
+        let docs = zigAnalysis.astNodes[decl.src].docs;
+        if (docs != null) {
+          tdDesc.innerHTML = shortDescMarkdown(docs);
+        } else {
+          tdDesc.textContent = "";
         }
+      }
+      domSectGlobalVars.classList.remove("hidden");
     }
 
-    function onHashChange() {
-        updateCurNav();
-        if (domSearch.value !== curNavSearch) {
-            domSearch.value = curNavSearch;
-        }
-        render();
-        if (imFeelingLucky) {
-            imFeelingLucky = false;
-            activateSelectedResult();
-        }
-    }
+    if (valsList.length !== 0) {
+      resizeDomList(
+        domListValues,
+        valsList.length,
+        '<tr><td><a href="#"></a></td><td></td><td></td></tr>'
+      );
+      for (let i = 0; i < valsList.length; i += 1) {
+        let decl = valsList[i];
+        let trDom = domListValues.children[i];
+
+        let tdName = trDom.children[0];
+        let tdNameA = tdName.children[0];
+        let tdType = trDom.children[1];
+        let tdDesc = trDom.children[2];
+
+        tdNameA.setAttribute("href", navLinkDecl(decl.name));
+        tdNameA.textContent = decl.name;
+
+        tdType.innerHTML = exprName(walkResultTypeRef(decl.value), {
+          wantHtml: true,
+          wantLink: true,
+        });
 
-    
-    function findSubDecl(parentType, childName) {
-        {
-            // Generic functions
-            if ("value" in parentType) {
-                const rv = resolveValue(parentType.value);
-                if ("type" in rv.expr) {
-                    const t = zigAnalysis.types[rv.expr.type];
-                    if (t.kind == typeKinds.Fn && t.generic_ret != null) {
-                        const rgr = resolveValue({expr: t.generic_ret});
-                        if ("type" in rgr.expr) {
-                            parentType = zigAnalysis.types[rgr.expr.type];
-                        }
-                    }
-                }
-            }
+        let docs = zigAnalysis.astNodes[decl.src].docs;
+        if (docs != null) {
+          tdDesc.innerHTML = shortDescMarkdown(docs);
+        } else {
+          tdDesc.textContent = "";
         }
+      }
+      domSectValues.classList.remove("hidden");
+    }
 
+    if (testsList.length !== 0) {
+      resizeDomList(
+        domListTests,
+        testsList.length,
+        '<tr><td><a href="#"></a></td><td></td><td></td></tr>'
+      );
+      for (let i = 0; i < testsList.length; i += 1) {
+        let decl = testsList[i];
+        let trDom = domListTests.children[i];
+
+        let tdName = trDom.children[0];
+        let tdNameA = tdName.children[0];
+        let tdType = trDom.children[1];
+        let tdDesc = trDom.children[2];
+
+        tdNameA.setAttribute("href", navLinkDecl(decl.name));
+        tdNameA.textContent = decl.name;
+
+        tdType.innerHTML = exprName(walkResultTypeRef(decl.value), {
+          wantHtml: true,
+          wantLink: true,
+        });
 
-        if (!parentType.pubDecls) return null;
-        for (let i = 0; i < parentType.pubDecls.length; i += 1) {
-            let declIndex = parentType.pubDecls[i];
-            let childDecl = zigAnalysis.decls[declIndex];
-            if (childDecl.name === childName) {
-                return childDecl;
-            }
-        }
-        if (!parentType.privDecls) return null;
-        for (let i = 0; i < parentType.privDecls.length; i += 1) {
-            let declIndex = parentType.privDecls[i];
-            let childDecl = zigAnalysis.decls[declIndex];
-            if (childDecl.name === childName) {
-                return childDecl;
-            }
+        let docs = zigAnalysis.astNodes[decl.src].docs;
+        if (docs != null) {
+          tdDesc.innerHTML = shortDescMarkdown(docs);
+        } else {
+          tdDesc.textContent = "";
         }
-        return null;
+      }
+      domSectTests.classList.remove("hidden");
     }
+  }
 
+  function operatorCompare(a, b) {
+    if (a === b) {
+      return 0;
+    } else if (a < b) {
+      return -1;
+    } else {
+      return 1;
+    }
+  }
 
+  function detectRootIsStd() {
+    let rootPkg = zigAnalysis.packages[zigAnalysis.rootPkg];
+    if (rootPkg.table["std"] == null) {
+      // no std mapped into the root package
+      return false;
+    }
+    let stdPkg = zigAnalysis.packages[rootPkg.table["std"]];
+    if (stdPkg == null) return false;
+    return rootPkg.file === stdPkg.file;
+  }
+
+  function indexTypeKinds() {
+    let map = {};
+    for (let i = 0; i < zigAnalysis.typeKinds.length; i += 1) {
+      map[zigAnalysis.typeKinds[i]] = i;
+    }
+    // This is just for debugging purposes, not needed to function
+    let assertList = [
+      "Type",
+      "Void",
+      "Bool",
+      "NoReturn",
+      "Int",
+      "Float",
+      "Pointer",
+      "Array",
+      "Struct",
+      "ComptimeFloat",
+      "ComptimeInt",
+      "Undefined",
+      "Null",
+      "Optional",
+      "ErrorUnion",
+      "ErrorSet",
+      "Enum",
+      "Union",
+      "Fn",
+      "BoundFn",
+      "Opaque",
+      "Frame",
+      "AnyFrame",
+      "Vector",
+      "EnumLiteral",
+    ];
+    for (let i = 0; i < assertList.length; i += 1) {
+      if (map[assertList[i]] == null)
+        throw new Error("No type kind '" + assertList[i] + "' found");
+    }
+    return map;
+  }
 
+  function findTypeTypeId() {
+    for (let i = 0; i < zigAnalysis.types.length; i += 1) {
+      if (zigAnalysis.types[i].kind == typeKinds.Type) {
+        return i;
+      }
+    }
+    throw new Error("No type 'type' found");
+  }
+
+  function updateCurNav() {
+    curNav = {
+      showPrivDecls: false,
+      pkgNames: [],
+      pkgObjs: [],
+      declNames: [],
+      declObjs: [],
+      callName: null,
+    };
+    curNavSearch = "";
 
-    function computeCanonicalPackagePaths() {
-        let list = new Array(zigAnalysis.packages.length);
-        // Now we try to find all the packages from root.
-        let rootPkg = zigAnalysis.packages[zigAnalysis.rootPkg];
-        // Breadth-first to keep the path shortest possible.
-        let stack = [{
-            path: ([]),
-            pkg: rootPkg,
-        }];
-        while (stack.length !== 0) {
-            let item = (stack.shift());
-            for (let key in item.pkg.table) {
-                let childPkgIndex = item.pkg.table[key];
-                if (list[childPkgIndex] != null) continue;
-                let childPkg = zigAnalysis.packages[childPkgIndex];
-                if (childPkg == null) continue;
+    if (location.hash[0] === "#" && location.hash.length > 1) {
+      let query = location.hash.substring(1);
+      if (query[0] === "*") {
+        curNav.showPrivDecls = true;
+        query = query.substring(1);
+      }
 
-                let newPath = item.path.concat([key])
-                list[childPkgIndex] = newPath;
-                stack.push({
-                    path: newPath,
-                    pkg: childPkg,
-                });
-            }
-        }
-        return list;
-    }
-
-
-    
-    function computeCanonDeclPaths() {
-        let list = new Array(zigAnalysis.decls.length);
-        canonTypeDecls = new Array(zigAnalysis.types.length);
-
-        for (let pkgI = 0; pkgI < zigAnalysis.packages.length; pkgI += 1) {
-            if (pkgI === zigAnalysis.rootPkg && rootIsStd) continue;
-            let pkg = zigAnalysis.packages[pkgI];
-            let pkgNames = canonPkgPaths[pkgI];
-            if (pkgNames === undefined) continue;
-
-            let stack = [{
-                declNames: ([]),
-                type: zigAnalysis.types[pkg.main],
-            }];
-            while (stack.length !== 0) {
-                let item = (stack.shift());
-
-                if (isContainerType(item.type)) {
-                    let t = (item.type);
-
-                    let len = t.pubDecls ? t.pubDecls.length : 0;
-                    for (let declI = 0; declI < len; declI += 1) {
-                        let mainDeclIndex = t.pubDecls[declI];
-                        if (list[mainDeclIndex] != null) continue;
-
-                        let decl = zigAnalysis.decls[mainDeclIndex];
-                        let declVal =  resolveValue(decl.value);
-                        let declNames = item.declNames.concat([decl.name]);
-                        list[mainDeclIndex] = {
-                            pkgNames: pkgNames,
-                            declNames: declNames,
-                        };
-                        if ("type" in declVal.expr) {
-                            let value = zigAnalysis.types[declVal.expr.type];
-                            if (declCanRepresentTypeKind(value.kind))
-                            {
-                                canonTypeDecls[declVal.type] = mainDeclIndex;
-                            }
-
-                            if (isContainerType(value)) {
-                                stack.push({
-                                    declNames: declNames,
-                                    type:value,
-                                });
-                            }
-                            
-                            
-                            // Generic fun/ction
-                            if (value.kind == typeKinds.Fn && value.generic_ret != null) {
-                                let resolvedVal = resolveValue({ expr: value.generic_ret});
-                                if ("type" in resolvedVal.expr) {
-                                    let generic_type = zigAnalysis.types[resolvedVal.expr.type];
-                                    if (isContainerType(generic_type)){
-                                        stack.push({
-                                            declNames: declNames,
-                                            type: generic_type,
-                                        });
-                                    }
-                                }
-                            }
-                        }
-                    }
-                }
-            }
-        }
-        return list;
-    }
+      let qpos = query.indexOf("?");
+      let nonSearchPart;
+      if (qpos === -1) {
+        nonSearchPart = query;
+      } else {
+        nonSearchPart = query.substring(0, qpos);
+        curNavSearch = decodeURIComponent(query.substring(qpos + 1));
+      }
 
-    
-    function getCanonDeclPath(index) {
-        if (canonDeclPaths == null) {
-            canonDeclPaths = computeCanonDeclPaths();
-        }
-        //let cd = (canonDeclPaths);
-        return canonDeclPaths[index];
+      let parts = nonSearchPart.split(";");
+      curNav.pkgNames = decodeURIComponent(parts[0]).split(".");
+      if (parts[1] != null) {
+        curNav.declNames = decodeURIComponent(parts[1]).split(".");
+      }
     }
+  }
 
-    
-    function getCanonTypeDecl(index) {
-        getCanonDeclPath(0);
-        //let ct = (canonTypeDecls);
-        return canonTypeDecls[index];
+  function onHashChange() {
+    updateCurNav();
+    if (domSearch.value !== curNavSearch) {
+      domSearch.value = curNavSearch;
     }
-
-    
-    function escapeHtml(text) {
-        return text.replace(/[&"<>]/g, function (m) {
-            return escapeHtmlReplacements[m];
-        });
+    render();
+    if (imFeelingLucky) {
+      imFeelingLucky = false;
+      activateSelectedResult();
     }
-
-
-    function shortDescMarkdown(docs) {
-        const trimmed_docs = docs.trim();
-        let index = trimmed_docs.indexOf('.');
-        if (index < 0) {
-            index = trimmed_docs.indexOf('\n');
-            if (index < 0) {
-                index = trimmed_docs.length;
+  }
+
+  function findSubDecl(parentType, childName) {
+    {
+      // Generic functions
+      if ("value" in parentType) {
+        const rv = resolveValue(parentType.value);
+        if ("type" in rv.expr) {
+          const t = zigAnalysis.types[rv.expr.type];
+          if (t.kind == typeKinds.Fn && t.generic_ret != null) {
+            const rgr = resolveValue({ expr: t.generic_ret });
+            if ("type" in rgr.expr) {
+              parentType = zigAnalysis.types[rgr.expr.type];
             }
-        } else {
-            index += 1; // include the period
+          }
         }
-        const slice = trimmed_docs.slice(0, index);
-        return markdown(slice);
+      }
     }
 
+    if (!parentType.pubDecls) return null;
+    for (let i = 0; i < parentType.pubDecls.length; i += 1) {
+      let declIndex = parentType.pubDecls[i];
+      let childDecl = zigAnalysis.decls[declIndex];
+      if (childDecl.name === childName) {
+        return childDecl;
+      }
+    }
+    if (!parentType.privDecls) return null;
+    for (let i = 0; i < parentType.privDecls.length; i += 1) {
+      let declIndex = parentType.privDecls[i];
+      let childDecl = zigAnalysis.decls[declIndex];
+      if (childDecl.name === childName) {
+        return childDecl;
+      }
+    }
+    return null;
+  }
+
+  function computeCanonicalPackagePaths() {
+    let list = new Array(zigAnalysis.packages.length);
+    // Now we try to find all the packages from root.
+    let rootPkg = zigAnalysis.packages[zigAnalysis.rootPkg];
+    // Breadth-first to keep the path shortest possible.
+    let stack = [
+      {
+        path: [],
+        pkg: rootPkg,
+      },
+    ];
+    while (stack.length !== 0) {
+      let item = stack.shift();
+      for (let key in item.pkg.table) {
+        let childPkgIndex = item.pkg.table[key];
+        if (list[childPkgIndex] != null) continue;
+        let childPkg = zigAnalysis.packages[childPkgIndex];
+        if (childPkg == null) continue;
+
+        let newPath = item.path.concat([key]);
+        list[childPkgIndex] = newPath;
+        stack.push({
+          path: newPath,
+          pkg: childPkg,
+        });
+      }
+    }
+    return list;
+  }
 
-    function markdown(input) {
-        const raw_lines = input.split('\n'); // zig allows no '\r', so we don't need to split on CR
-        
-        const lines = [];
-
-        // PHASE 1:
-        // Dissect lines and determine the type for each line.
-            // Also computes indentation level and removes unnecessary whitespace
+  function computeCanonDeclPaths() {
+    let list = new Array(zigAnalysis.decls.length);
+    canonTypeDecls = new Array(zigAnalysis.types.length);
 
-        let is_reading_code = false;
-        let code_indent = 0;
-        for (let line_no = 0; line_no < raw_lines.length; line_no++) {
-            const raw_line = raw_lines[line_no];
+    for (let pkgI = 0; pkgI < zigAnalysis.packages.length; pkgI += 1) {
+      if (pkgI === zigAnalysis.rootPkg && rootIsStd) continue;
+      let pkg = zigAnalysis.packages[pkgI];
+      let pkgNames = canonPkgPaths[pkgI];
+      if (pkgNames === undefined) continue;
 
-            const line = {
-                indent: 0,
-                raw_text: raw_line,
-                text: raw_line.trim(),
-                type: "p", // p, h1 โ€ฆ h6, code, ul, ol, blockquote, skip, empty
-                ordered_number: -1, // NOTE: hack to make the type checker happy
+      let stack = [
+        {
+          declNames: [],
+          type: zigAnalysis.types[pkg.main],
+        },
+      ];
+      while (stack.length !== 0) {
+        let item = stack.shift();
+
+        if (isContainerType(item.type)) {
+          let t = item.type;
+
+          let len = t.pubDecls ? t.pubDecls.length : 0;
+          for (let declI = 0; declI < len; declI += 1) {
+            let mainDeclIndex = t.pubDecls[declI];
+            if (list[mainDeclIndex] != null) continue;
+
+            let decl = zigAnalysis.decls[mainDeclIndex];
+            let declVal = resolveValue(decl.value);
+            let declNames = item.declNames.concat([decl.name]);
+            list[mainDeclIndex] = {
+              pkgNames: pkgNames,
+              declNames: declNames,
             };
+            if ("type" in declVal.expr) {
+              let value = zigAnalysis.types[declVal.expr.type];
+              if (declCanRepresentTypeKind(value.kind)) {
+                canonTypeDecls[declVal.type] = mainDeclIndex;
+              }
 
-            if (!is_reading_code) {
-                while ((line.indent < line.raw_text.length) && line.raw_text[line.indent] == ' ') {
-                    line.indent += 1;
-                }
+              if (isContainerType(value)) {
+                stack.push({
+                  declNames: declNames,
+                  type: value,
+                });
+              }
 
-                if (line.text.startsWith("######")) {
-                    line.type = "h6";
-                    line.text = line.text.substr(6);
-                }
-                else if (line.text.startsWith("#####")) {
-                    line.type = "h5";
-                    line.text = line.text.substr(5);
-                }
-                else if (line.text.startsWith("####")) {
-                    line.type = "h4";
-                    line.text = line.text.substr(4);
-                }
-                else if (line.text.startsWith("###")) {
-                    line.type = "h3";
-                    line.text = line.text.substr(3);
-                }
-                else if (line.text.startsWith("##")) {
-                    line.type = "h2";
-                    line.text = line.text.substr(2);
-                }
-                else if (line.text.startsWith("#")) {
-                    line.type = "h1";
-                    line.text = line.text.substr(1);
-                }
-                else if (line.text.startsWith("-")) {
-                    line.type = "ul";
-                    line.text = line.text.substr(1);
-                }
-                else if (line.text.match(/^\d+\..*$/)) { // if line starts with {number}{dot}
-                    const match = (line.text.match(/(\d+)\./));
-                    line.type = "ul";
-                    line.text = line.text.substr(match[0].length);
-                    line.ordered_number = Number(match[1].length);
-                }
-                else if (line.text == "```") {
-                    line.type = "skip";
-                    is_reading_code = true;
-                    code_indent = line.indent;
-                }
-                else if (line.text == "") {
-                    line.type = "empty";
-                }
-            }
-            else {
-                if (line.text == "```") {
-                    is_reading_code = false;
-                    line.type = "skip";
-                } else {
-                    line.type = "code";
-                    line.text = line.raw_text.substr(code_indent); // remove the indent of the ``` from all the code block
+              // Generic fun/ction
+              if (value.kind == typeKinds.Fn && value.generic_ret != null) {
+                let resolvedVal = resolveValue({ expr: value.generic_ret });
+                if ("type" in resolvedVal.expr) {
+                  let generic_type = zigAnalysis.types[resolvedVal.expr.type];
+                  if (isContainerType(generic_type)) {
+                    stack.push({
+                      declNames: declNames,
+                      type: generic_type,
+                    });
+                  }
                 }
+              }
             }
+          }
+        }
+      }
+    }
+    return list;
+  }
 
-            if (line.type != "skip") {
-                lines.push(line);
-            }
+  function getCanonDeclPath(index) {
+    if (canonDeclPaths == null) {
+      canonDeclPaths = computeCanonDeclPaths();
+    }
+    //let cd = (canonDeclPaths);
+    return canonDeclPaths[index];
+  }
+
+  function getCanonTypeDecl(index) {
+    getCanonDeclPath(0);
+    //let ct = (canonTypeDecls);
+    return canonTypeDecls[index];
+  }
+
+  function escapeHtml(text) {
+    return text.replace(/[&"<>]/g, function (m) {
+      return escapeHtmlReplacements[m];
+    });
+  }
+
+  function shortDescMarkdown(docs) {
+    const trimmed_docs = docs.trim();
+    let index = trimmed_docs.indexOf(".");
+    if (index < 0) {
+      index = trimmed_docs.indexOf("\n");
+      if (index < 0) {
+        index = trimmed_docs.length;
+      }
+    } else {
+      index += 1; // include the period
+    }
+    const slice = trimmed_docs.slice(0, index);
+    return markdown(slice);
+  }
+
+  function markdown(input) {
+    const raw_lines = input.split("\n"); // zig allows no '\r', so we don't need to split on CR
+
+    const lines = [];
+
+    // PHASE 1:
+    // Dissect lines and determine the type for each line.
+    // Also computes indentation level and removes unnecessary whitespace
+
+    let is_reading_code = false;
+    let code_indent = 0;
+    for (let line_no = 0; line_no < raw_lines.length; line_no++) {
+      const raw_line = raw_lines[line_no];
+
+      const line = {
+        indent: 0,
+        raw_text: raw_line,
+        text: raw_line.trim(),
+        type: "p", // p, h1 โ€ฆ h6, code, ul, ol, blockquote, skip, empty
+        ordered_number: -1, // NOTE: hack to make the type checker happy
+      };
+
+      if (!is_reading_code) {
+        while (
+          line.indent < line.raw_text.length &&
+          line.raw_text[line.indent] == " "
+        ) {
+          line.indent += 1;
+        }
+
+        if (line.text.startsWith("######")) {
+          line.type = "h6";
+          line.text = line.text.substr(6);
+        } else if (line.text.startsWith("#####")) {
+          line.type = "h5";
+          line.text = line.text.substr(5);
+        } else if (line.text.startsWith("####")) {
+          line.type = "h4";
+          line.text = line.text.substr(4);
+        } else if (line.text.startsWith("###")) {
+          line.type = "h3";
+          line.text = line.text.substr(3);
+        } else if (line.text.startsWith("##")) {
+          line.type = "h2";
+          line.text = line.text.substr(2);
+        } else if (line.text.startsWith("#")) {
+          line.type = "h1";
+          line.text = line.text.substr(1);
+        } else if (line.text.startsWith("-")) {
+          line.type = "ul";
+          line.text = line.text.substr(1);
+        } else if (line.text.match(/^\d+\..*$/)) {
+          // if line starts with {number}{dot}
+          const match = line.text.match(/(\d+)\./);
+          line.type = "ul";
+          line.text = line.text.substr(match[0].length);
+          line.ordered_number = Number(match[1].length);
+        } else if (line.text == "```") {
+          line.type = "skip";
+          is_reading_code = true;
+          code_indent = line.indent;
+        } else if (line.text == "") {
+          line.type = "empty";
+        }
+      } else {
+        if (line.text == "```") {
+          is_reading_code = false;
+          line.type = "skip";
+        } else {
+          line.type = "code";
+          line.text = line.raw_text.substr(code_indent); // remove the indent of the ``` from all the code block
         }
+      }
 
-        // PHASE 2:
-        // Render HTML from markdown lines.
-            // Look at each line and emit fitting HTML code
-
-        
-        function markdownInlines(innerText) {
-
-            // inline types:
-            // **{INLINE}**       : <strong>
-                // __{INLINE}__       : <u>
-                // ~~{INLINE}~~       : <s>
-                //  *{INLINE}*        : <emph>
-                //  _{INLINE}_        : <emph>
-                //  `{TEXT}`          : <code>
-                //  [{INLINE}]({URL}) : <a>
-                // ![{TEXT}]({URL})   : <img>
-                // [[std;format.fmt]] : <a> (inner link)
-
-            
-            
-            const formats = [
-                {
-                    marker: "**",
-                    tag: "strong",
-                },
-                {
-                    marker: "~~",
-                    tag: "s",
-                },
-                {
-                    marker: "__",
-                    tag: "u",
-                },
-                {
-                    marker: "*",
-                    tag: "em",
-                }
-            ];
+      if (line.type != "skip") {
+        lines.push(line);
+      }
+    }
 
-            
-            const stack = [];
+    // PHASE 2:
+    // Render HTML from markdown lines.
+    // Look at each line and emit fitting HTML code
+
+    function markdownInlines(innerText) {
+      // inline types:
+      // **{INLINE}**       : <strong>
+      // __{INLINE}__       : <u>
+      // ~~{INLINE}~~       : <s>
+      //  *{INLINE}*        : <emph>
+      //  _{INLINE}_        : <emph>
+      //  `{TEXT}`          : <code>
+      //  [{INLINE}]({URL}) : <a>
+      // ![{TEXT}]({URL})   : <img>
+      // [[std;format.fmt]] : <a> (inner link)
+
+      const formats = [
+        {
+          marker: "**",
+          tag: "strong",
+        },
+        {
+          marker: "~~",
+          tag: "s",
+        },
+        {
+          marker: "__",
+          tag: "u",
+        },
+        {
+          marker: "*",
+          tag: "em",
+        },
+      ];
 
-            let innerHTML = "";
-            let currentRun = "";
+      const stack = [];
 
-            function flushRun() {
-                if (currentRun != "") {
-                    innerHTML += escapeHtml(currentRun);
-                }
-                currentRun = "";
-            }
+      let innerHTML = "";
+      let currentRun = "";
 
-            let parsing_code = false;
-            let codetag = "";
-            let in_code = false;
-
-            for (let i = 0; i < innerText.length; i++) {
-
-                if (parsing_code && in_code) {
-                    if (innerText.substr(i, codetag.length) == codetag) {
-                        // remove leading and trailing whitespace if string both starts and ends with one.
-                            if (currentRun[0] == " " && currentRun[currentRun.length - 1] == " ") {
-                                currentRun = currentRun.substr(1, currentRun.length - 2);
-                            }
-                        flushRun();
-                        i += codetag.length - 1;
-                        in_code = false;
-                        parsing_code = false;
-                        innerHTML += "</code>";
-                        codetag = "";
-                    } else {
-                        currentRun += innerText[i];
-                    }
-                    continue;
-                }
+      function flushRun() {
+        if (currentRun != "") {
+          innerHTML += escapeHtml(currentRun);
+        }
+        currentRun = "";
+      }
 
-                if (innerText[i] == "`") {
-                    flushRun();
-                    if (!parsing_code) {
-                        innerHTML += "<code>";
-                    }
-                    parsing_code = true;
-                    codetag += "`";
-                    continue;
-                }
+      let parsing_code = false;
+      let codetag = "";
+      let in_code = false;
 
-                if (parsing_code) {
-                    currentRun += innerText[i];
-                    in_code = true;
-                } else {
-                    let any = false;
-                    for (let idx = (stack.length > 0 ? -1 : 0); idx < formats.length; idx++) {
-                        const fmt = idx >= 0 ? formats[idx] : stack[stack.length - 1];
-                        if (innerText.substr(i, fmt.marker.length) == fmt.marker) {
-                            flushRun();
-                            if (stack[stack.length - 1] == fmt) {
-                                stack.pop();
-                                innerHTML += "</" + fmt.tag + ">";
-                            } else {
-                                stack.push(fmt);
-                                innerHTML += "<" + fmt.tag + ">";
-                            }
-                            i += fmt.marker.length - 1;
-                            any = true;
-                            break;
-                        }
-                    }
-                    if (!any) {
-                        currentRun += innerText[i];
-                    }
-                }
+      for (let i = 0; i < innerText.length; i++) {
+        if (parsing_code && in_code) {
+          if (innerText.substr(i, codetag.length) == codetag) {
+            // remove leading and trailing whitespace if string both starts and ends with one.
+            if (
+              currentRun[0] == " " &&
+              currentRun[currentRun.length - 1] == " "
+            ) {
+              currentRun = currentRun.substr(1, currentRun.length - 2);
             }
             flushRun();
-
-            while (stack.length > 0) {
-                const fmt = (stack.pop());
-                innerHTML += "</" + fmt.tag + ">";
-            }
-
-            return innerHTML;
-        }
-
-        
-        function previousLineIs(type, line_no) {
-            if (line_no > 0) {
-                return (lines[line_no - 1].type == type);
-            } else {
-                return false;
-            }
+            i += codetag.length - 1;
+            in_code = false;
+            parsing_code = false;
+            innerHTML += "</code>";
+            codetag = "";
+          } else {
+            currentRun += innerText[i];
+          }
+          continue;
         }
 
-        
-        function nextLineIs(type, line_no) {
-            if (line_no < (lines.length - 1)) {
-                return (lines[line_no + 1].type == type);
-            } else {
-                return false;
-            }
+        if (innerText[i] == "`") {
+          flushRun();
+          if (!parsing_code) {
+            innerHTML += "<code>";
+          }
+          parsing_code = true;
+          codetag += "`";
+          continue;
         }
 
-        
-        function getPreviousLineIndent(line_no) {
-            if (line_no > 0) {
-                return lines[line_no - 1].indent;
-            } else {
-                return 0;
+        if (parsing_code) {
+          currentRun += innerText[i];
+          in_code = true;
+        } else {
+          let any = false;
+          for (
+            let idx = stack.length > 0 ? -1 : 0;
+            idx < formats.length;
+            idx++
+          ) {
+            const fmt = idx >= 0 ? formats[idx] : stack[stack.length - 1];
+            if (innerText.substr(i, fmt.marker.length) == fmt.marker) {
+              flushRun();
+              if (stack[stack.length - 1] == fmt) {
+                stack.pop();
+                innerHTML += "</" + fmt.tag + ">";
+              } else {
+                stack.push(fmt);
+                innerHTML += "<" + fmt.tag + ">";
+              }
+              i += fmt.marker.length - 1;
+              any = true;
+              break;
             }
+          }
+          if (!any) {
+            currentRun += innerText[i];
+          }
         }
+      }
+      flushRun();
 
-        
-        function getNextLineIndent(line_no) {
-            if (line_no < (lines.length - 1)) {
-                return lines[line_no + 1].indent;
-            } else {
-                return 0;
-            }
-        }
+      while (stack.length > 0) {
+        const fmt = stack.pop();
+        innerHTML += "</" + fmt.tag + ">";
+      }
 
-        let html = "";
-        for (let line_no = 0; line_no < lines.length; line_no++) {
-            const line = lines[line_no];
+      return innerHTML;
+    }
 
+    function previousLineIs(type, line_no) {
+      if (line_no > 0) {
+        return lines[line_no - 1].type == type;
+      } else {
+        return false;
+      }
+    }
 
+    function nextLineIs(type, line_no) {
+      if (line_no < lines.length - 1) {
+        return lines[line_no + 1].type == type;
+      } else {
+        return false;
+      }
+    }
 
-            switch (line.type) {
-                case "h1":
-                case "h2":
-                case "h3":
-                case "h4":
-                case "h5":
-                case "h6":
-                    html += "<" + line.type + ">" + markdownInlines(line.text) + "</" + line.type + ">\n";
-                    break;
+    function getPreviousLineIndent(line_no) {
+      if (line_no > 0) {
+        return lines[line_no - 1].indent;
+      } else {
+        return 0;
+      }
+    }
 
-                case "ul":
-                case "ol":
-                    if (!previousLineIs("ul", line_no) || getPreviousLineIndent(line_no) < line.indent) {
-                        html += "<" + line.type + ">\n";
-                    }
+    function getNextLineIndent(line_no) {
+      if (line_no < lines.length - 1) {
+        return lines[line_no + 1].indent;
+      } else {
+        return 0;
+      }
+    }
 
-                    html += "<li>" + markdownInlines(line.text) + "</li>\n";
+    let html = "";
+    for (let line_no = 0; line_no < lines.length; line_no++) {
+      const line = lines[line_no];
+
+      switch (line.type) {
+        case "h1":
+        case "h2":
+        case "h3":
+        case "h4":
+        case "h5":
+        case "h6":
+          html +=
+            "<" +
+            line.type +
+            ">" +
+            markdownInlines(line.text) +
+            "</" +
+            line.type +
+            ">\n";
+          break;
+
+        case "ul":
+        case "ol":
+          if (
+            !previousLineIs("ul", line_no) ||
+            getPreviousLineIndent(line_no) < line.indent
+          ) {
+            html += "<" + line.type + ">\n";
+          }
 
-                    if (!nextLineIs("ul", line_no) || getNextLineIndent(line_no) < line.indent) {
-                        html += "</" + line.type + ">\n";
-                    }
-                    break;
+          html += "<li>" + markdownInlines(line.text) + "</li>\n";
 
-                case "p":
-                    if (!previousLineIs("p", line_no)) {
-                        html += "<p>\n";
-                    }
-                    html += markdownInlines(line.text) + "\n";
-                    if (!nextLineIs("p", line_no)) {
-                        html += "</p>\n";
-                    }
-                    break;
+          if (
+            !nextLineIs("ul", line_no) ||
+            getNextLineIndent(line_no) < line.indent
+          ) {
+            html += "</" + line.type + ">\n";
+          }
+          break;
 
-                case "code":
-                    if (!previousLineIs("code", line_no)) {
-                        html += "<pre><code>";
-                    }
-                    html += escapeHtml(line.text) + "\n";
-                    if (!nextLineIs("code", line_no)) {
-                        html += "</code></pre>\n";
-                    }
-                    break;
-            }
-        }
+        case "p":
+          if (!previousLineIs("p", line_no)) {
+            html += "<p>\n";
+          }
+          html += markdownInlines(line.text) + "\n";
+          if (!nextLineIs("p", line_no)) {
+            html += "</p>\n";
+          }
+          break;
 
-        return html;
+        case "code":
+          if (!previousLineIs("code", line_no)) {
+            html += "<pre><code>";
+          }
+          html += escapeHtml(line.text) + "\n";
+          if (!nextLineIs("code", line_no)) {
+            html += "</code></pre>\n";
+          }
+          break;
+      }
     }
 
-    function activateSelectedResult() {
-        if (domSectSearchResults.classList.contains("hidden")) {
-            return;
-        }
+    return html;
+  }
 
-        let liDom = domListSearchResults.children[curSearchIndex];
-        if (liDom == null && domListSearchResults.children.length !== 0) {
-            liDom = domListSearchResults.children[0];
-        }
-        if (liDom != null) {
-            let aDom = liDom.children[0];
-            location.href = (aDom.getAttribute("href"));
-            curSearchIndex = -1;
-        }
-        domSearch.blur();
+  function activateSelectedResult() {
+    if (domSectSearchResults.classList.contains("hidden")) {
+      return;
     }
 
-    
-    function onSearchKeyDown(ev) {
-        switch (getKeyString(ev)) {
-            case "Enter":
-                // detect if this search changes anything
-                let terms1 = getSearchTerms();
-                startSearch();
-                updateCurNav();
-                let terms2 = getSearchTerms();
-                // we might have to wait for onHashChange to trigger
-                imFeelingLucky = (terms1.join(' ') !== terms2.join(' '));
-                if (!imFeelingLucky) activateSelectedResult();
-
-                ev.preventDefault();
-                ev.stopPropagation();
-                return;
-            case "Esc":
-                domSearch.value = "";
-                domSearch.blur();
-                curSearchIndex = -1;
-                ev.preventDefault();
-                ev.stopPropagation();
-                startSearch();
-                return;
-            case "Up":
-                moveSearchCursor(-1);
-                ev.preventDefault();
-                ev.stopPropagation();
-                return;
-            case "Down":
-                moveSearchCursor(1);
-                ev.preventDefault();
-                ev.stopPropagation();
-                return;
-            default:
-                if (ev.shiftKey || ev.ctrlKey || ev.altKey) return;
-
-                curSearchIndex = -1;
-                ev.stopPropagation();
-                startAsyncSearch();
-                return;
-        }
+    let liDom = domListSearchResults.children[curSearchIndex];
+    if (liDom == null && domListSearchResults.children.length !== 0) {
+      liDom = domListSearchResults.children[0];
     }
-
-
-    
-    function moveSearchCursor(dir) {
-        if (curSearchIndex < 0 || curSearchIndex >= domListSearchResults.children.length) {
-            if (dir > 0) {
-                curSearchIndex = -1 + dir;
-            } else if (dir < 0) {
-                curSearchIndex = domListSearchResults.children.length + dir;
-            }
-        } else {
-            curSearchIndex += dir;
-        }
-        if (curSearchIndex < 0) {
-            curSearchIndex = 0;
-        }
-        if (curSearchIndex >= domListSearchResults.children.length) {
-            curSearchIndex = domListSearchResults.children.length - 1;
-        }
-        renderSearchCursor();
+    if (liDom != null) {
+      let aDom = liDom.children[0];
+      location.href = aDom.getAttribute("href");
+      curSearchIndex = -1;
     }
-
-    
-    function getKeyString(ev) {
-        let name;
-        let ignoreShift = false;
-        switch (ev.which) {
-            case 13:
-                name = "Enter";
-                break;
-            case 27:
-                name = "Esc";
-                break;
-            case 38:
-                name = "Up";
-                break;
-            case 40:
-                name = "Down";
-                break;
-            default:
-                ignoreShift = true;
-                name = (ev.key != null) ? ev.key : String.fromCharCode(ev.charCode || ev.keyCode);
-        }
-        if (!ignoreShift && ev.shiftKey) name = "Shift+" + name;
-        if (ev.altKey) name = "Alt+" + name;
-        if (ev.ctrlKey) name = "Ctrl+" + name;
-        return name;
+    domSearch.blur();
+  }
+
+  function onSearchKeyDown(ev) {
+    switch (getKeyString(ev)) {
+      case "Enter":
+        // detect if this search changes anything
+        let terms1 = getSearchTerms();
+        startSearch();
+        updateCurNav();
+        let terms2 = getSearchTerms();
+        // we might have to wait for onHashChange to trigger
+        imFeelingLucky = terms1.join(" ") !== terms2.join(" ");
+        if (!imFeelingLucky) activateSelectedResult();
+
+        ev.preventDefault();
+        ev.stopPropagation();
+        return;
+      case "Esc":
+        domSearch.value = "";
+        domSearch.blur();
+        curSearchIndex = -1;
+        ev.preventDefault();
+        ev.stopPropagation();
+        startSearch();
+        return;
+      case "Up":
+        moveSearchCursor(-1);
+        ev.preventDefault();
+        ev.stopPropagation();
+        return;
+      case "Down":
+        moveSearchCursor(1);
+        ev.preventDefault();
+        ev.stopPropagation();
+        return;
+      default:
+        if (ev.shiftKey || ev.ctrlKey || ev.altKey) return;
+
+        curSearchIndex = -1;
+        ev.stopPropagation();
+        startAsyncSearch();
+        return;
     }
-
-    
-    function onWindowKeyDown(ev) {
-        switch (getKeyString(ev)) {
-            case "Esc":
-                if (!domHelpModal.classList.contains("hidden")) {
-                    domHelpModal.classList.add("hidden");
-                    ev.preventDefault();
-                    ev.stopPropagation();
-                }
-                break;
-            case "s":
-                domSearch.focus();
-                domSearch.select();
-                ev.preventDefault();
-                ev.stopPropagation();
-                startAsyncSearch();
-                break;
-            case "?":
-                    ev.preventDefault();
-                ev.stopPropagation();
-                showHelpModal();
-                break;
-        }
+  }
+
+  function moveSearchCursor(dir) {
+    if (
+      curSearchIndex < 0 ||
+      curSearchIndex >= domListSearchResults.children.length
+    ) {
+      if (dir > 0) {
+        curSearchIndex = -1 + dir;
+      } else if (dir < 0) {
+        curSearchIndex = domListSearchResults.children.length + dir;
+      }
+    } else {
+      curSearchIndex += dir;
+    }
+    if (curSearchIndex < 0) {
+      curSearchIndex = 0;
+    }
+    if (curSearchIndex >= domListSearchResults.children.length) {
+      curSearchIndex = domListSearchResults.children.length - 1;
+    }
+    renderSearchCursor();
+  }
+
+  function getKeyString(ev) {
+    let name;
+    let ignoreShift = false;
+    switch (ev.which) {
+      case 13:
+        name = "Enter";
+        break;
+      case 27:
+        name = "Esc";
+        break;
+      case 38:
+        name = "Up";
+        break;
+      case 40:
+        name = "Down";
+        break;
+      default:
+        ignoreShift = true;
+        name =
+          ev.key != null
+            ? ev.key
+            : String.fromCharCode(ev.charCode || ev.keyCode);
+    }
+    if (!ignoreShift && ev.shiftKey) name = "Shift+" + name;
+    if (ev.altKey) name = "Alt+" + name;
+    if (ev.ctrlKey) name = "Ctrl+" + name;
+    return name;
+  }
+
+  function onWindowKeyDown(ev) {
+    switch (getKeyString(ev)) {
+      case "Esc":
+        if (!domHelpModal.classList.contains("hidden")) {
+          domHelpModal.classList.add("hidden");
+          ev.preventDefault();
+          ev.stopPropagation();
+        }
+        break;
+      case "s":
+        domSearch.focus();
+        domSearch.select();
+        ev.preventDefault();
+        ev.stopPropagation();
+        startAsyncSearch();
+        break;
+      case "?":
+        ev.preventDefault();
+        ev.stopPropagation();
+        showHelpModal();
+        break;
     }
+  }
 
-function showHelpModal() {
+  function showHelpModal() {
     domHelpModal.classList.remove("hidden");
-    domHelpModal.style.left = (window.innerWidth / 2 - domHelpModal.clientWidth / 2) + "px";
-    domHelpModal.style.top = (window.innerHeight / 2 - domHelpModal.clientHeight / 2) + "px";
+    domHelpModal.style.left =
+      window.innerWidth / 2 - domHelpModal.clientWidth / 2 + "px";
+    domHelpModal.style.top =
+      window.innerHeight / 2 - domHelpModal.clientHeight / 2 + "px";
     domHelpModal.focus();
-}
+  }
 
-function clearAsyncSearch() {
+  function clearAsyncSearch() {
     if (searchTimer != null) {
-        clearTimeout(searchTimer);
-        searchTimer = null;
+      clearTimeout(searchTimer);
+      searchTimer = null;
     }
-}
+  }
 
-function startAsyncSearch() {
+  function startAsyncSearch() {
     clearAsyncSearch();
     searchTimer = setTimeout(startSearch, 100);
-}
-function startSearch() {
+  }
+  function startSearch() {
     clearAsyncSearch();
     let oldHash = location.hash;
     let parts = oldHash.split("?");
-    let newPart2 = (domSearch.value === "") ? "" : ("?" + domSearch.value);
-    location.hash = (parts.length === 1) ? (oldHash + newPart2) : (parts[0] + newPart2);
-}
-function getSearchTerms() {
+    let newPart2 = domSearch.value === "" ? "" : "?" + domSearch.value;
+    location.hash =
+      parts.length === 1 ? oldHash + newPart2 : parts[0] + newPart2;
+  }
+  function getSearchTerms() {
     let list = curNavSearch.trim().split(/[ \r\n\t]+/);
     list.sort();
     return list;
-}
-function renderSearch() {
+  }
+  function renderSearch() {
     let matchedItems = [];
-    let ignoreCase = (curNavSearch.toLowerCase() === curNavSearch);
+    let ignoreCase = curNavSearch.toLowerCase() === curNavSearch;
     let terms = getSearchTerms();
 
-    decl_loop: for (let declIndex = 0; declIndex < zigAnalysis.decls.length; declIndex += 1) {
-        let canonPath = getCanonDeclPath(declIndex);
-        if (canonPath == null) continue;
-
-        let decl = zigAnalysis.decls[declIndex];
-        let lastPkgName = canonPath.pkgNames[canonPath.pkgNames.length - 1];
-        let fullPathSearchText = lastPkgName + "." + canonPath.declNames.join('.');
-        let astNode = zigAnalysis.astNodes[decl.src];
-        let fileAndDocs = "" //zigAnalysis.files[astNode.file];
-        // TODO: understand what this piece of code is trying to achieve
-        //       also right now `files` are expressed as a hashmap.
-        if (astNode.docs != null) {
-            fileAndDocs += "\n" + astNode.docs;
-        }
-        let fullPathSearchTextLower = fullPathSearchText;
-        if (ignoreCase) {
-            fullPathSearchTextLower = fullPathSearchTextLower.toLowerCase();
-            fileAndDocs = fileAndDocs.toLowerCase();
-        }
-
-        let points = 0;
-        for (let termIndex = 0; termIndex < terms.length; termIndex += 1) {
-            let term = terms[termIndex];
+    decl_loop: for (
+      let declIndex = 0;
+      declIndex < zigAnalysis.decls.length;
+      declIndex += 1
+    ) {
+      let canonPath = getCanonDeclPath(declIndex);
+      if (canonPath == null) continue;
+
+      let decl = zigAnalysis.decls[declIndex];
+      let lastPkgName = canonPath.pkgNames[canonPath.pkgNames.length - 1];
+      let fullPathSearchText =
+        lastPkgName + "." + canonPath.declNames.join(".");
+      let astNode = zigAnalysis.astNodes[decl.src];
+      let fileAndDocs = ""; //zigAnalysis.files[astNode.file];
+      // TODO: understand what this piece of code is trying to achieve
+      //       also right now `files` are expressed as a hashmap.
+      if (astNode.docs != null) {
+        fileAndDocs += "\n" + astNode.docs;
+      }
+      let fullPathSearchTextLower = fullPathSearchText;
+      if (ignoreCase) {
+        fullPathSearchTextLower = fullPathSearchTextLower.toLowerCase();
+        fileAndDocs = fileAndDocs.toLowerCase();
+      }
 
-            // exact, case sensitive match of full decl path
-            if (fullPathSearchText === term) {
-                points += 4;
-                continue;
-            }
-            // exact, case sensitive match of just decl name
-            if (decl.name == term) {
-                points += 3;
-                continue;
-            }
-            // substring, case insensitive match of full decl path
-            if (fullPathSearchTextLower.indexOf(term) >= 0) {
-                points += 2;
-                continue;
-            }
-            if (fileAndDocs.indexOf(term) >= 0) {
-                points += 1;
-                continue;
-            }
+      let points = 0;
+      for (let termIndex = 0; termIndex < terms.length; termIndex += 1) {
+        let term = terms[termIndex];
 
-            continue decl_loop;
+        // exact, case sensitive match of full decl path
+        if (fullPathSearchText === term) {
+          points += 4;
+          continue;
+        }
+        // exact, case sensitive match of just decl name
+        if (decl.name == term) {
+          points += 3;
+          continue;
+        }
+        // substring, case insensitive match of full decl path
+        if (fullPathSearchTextLower.indexOf(term) >= 0) {
+          points += 2;
+          continue;
+        }
+        if (fileAndDocs.indexOf(term) >= 0) {
+          points += 1;
+          continue;
         }
 
-        matchedItems.push({
-            decl: decl,
-            path: canonPath,
-            points: points,
-        });
+        continue decl_loop;
+      }
+
+      matchedItems.push({
+        decl: decl,
+        path: canonPath,
+        points: points,
+      });
     }
 
     if (matchedItems.length !== 0) {
-        resizeDomList(domListSearchResults, matchedItems.length, '<li><a href="#"></a></li>');
-
-        matchedItems.sort(function(a, b) {
-            let cmp = operatorCompare(b.points, a.points);
-            if (cmp != 0) return cmp;
-            return operatorCompare(a.decl.name, b.decl.name);
-        });
-
-        for (let i = 0; i < matchedItems.length; i += 1) {
-            let liDom = domListSearchResults.children[i];
-            let aDom = liDom.children[0];
-            let match = matchedItems[i];
-            let lastPkgName = match.path.pkgNames[match.path.pkgNames.length - 1];
-            aDom.textContent = lastPkgName + "." + match.path.declNames.join('.');
-            aDom.setAttribute('href', navLink(match.path.pkgNames, match.path.declNames));
-        }
-        renderSearchCursor();
+      resizeDomList(
+        domListSearchResults,
+        matchedItems.length,
+        '<li><a href="#"></a></li>'
+      );
+
+      matchedItems.sort(function (a, b) {
+        let cmp = operatorCompare(b.points, a.points);
+        if (cmp != 0) return cmp;
+        return operatorCompare(a.decl.name, b.decl.name);
+      });
+
+      for (let i = 0; i < matchedItems.length; i += 1) {
+        let liDom = domListSearchResults.children[i];
+        let aDom = liDom.children[0];
+        let match = matchedItems[i];
+        let lastPkgName = match.path.pkgNames[match.path.pkgNames.length - 1];
+        aDom.textContent = lastPkgName + "." + match.path.declNames.join(".");
+        aDom.setAttribute(
+          "href",
+          navLink(match.path.pkgNames, match.path.declNames)
+        );
+      }
+      renderSearchCursor();
 
-        domSectSearchResults.classList.remove("hidden");
+      domSectSearchResults.classList.remove("hidden");
     } else {
-        domSectSearchNoResults.classList.remove("hidden");
+      domSectSearchNoResults.classList.remove("hidden");
     }
-}
+  }
 
-function renderSearchCursor() {
+  function renderSearchCursor() {
     for (let i = 0; i < domListSearchResults.children.length; i += 1) {
-        let liDom = (domListSearchResults.children[i]);
-        if (curSearchIndex === i) {
-            liDom.classList.add("selected");
-        } else {
-            liDom.classList.remove("selected");
-        }
+      let liDom = domListSearchResults.children[i];
+      if (curSearchIndex === i) {
+        liDom.classList.add("selected");
+      } else {
+        liDom.classList.remove("selected");
+      }
     }
-}
-
-
-
-// function indexNodesToCalls() {
-//     let map = {};
-//     for (let i = 0; i < zigAnalysis.calls.length; i += 1) {
-//         let call = zigAnalysis.calls[i];
-//         let fn = zigAnalysis.fns[call.fn];
-//         if (map[fn.src] == null) {
-//             map[fn.src] = [i];
-//         } else {
-//             map[fn.src].push(i);
-//         }
-//     }
-//     return map;
-// }
-
-
-
-function byNameProperty(a, b) {
+  }
+
+  // function indexNodesToCalls() {
+  //     let map = {};
+  //     for (let i = 0; i < zigAnalysis.calls.length; i += 1) {
+  //         let call = zigAnalysis.calls[i];
+  //         let fn = zigAnalysis.fns[call.fn];
+  //         if (map[fn.src] == null) {
+  //             map[fn.src] = [i];
+  //         } else {
+  //             map[fn.src].push(i);
+  //         }
+  //     }
+  //     return map;
+  // }
+
+  function byNameProperty(a, b) {
     return operatorCompare(a.name, b.name);
-}
-
-
-
+  }
 })();