diff --git a/ivette/package.json b/ivette/package.json
index 88b867fbf7caa9cf4ba46ad42277eb724627bf7b..d111ed48493696ca2463aac7a4c9c07f987ecd02 100644
--- a/ivette/package.json
+++ b/ivette/package.json
@@ -46,6 +46,7 @@
     "react-dom": "^18",
     "react-draggable": "^4.4.6",
     "react-fast-compare": "^3.2.2",
+    "react-infinite-scroller": "^1.2.6",
     "react-pivottable": "^0.11.0",
     "react-virtualized": "9.22.5",
     "react-virtualized-auto-sizer": "^1.0.22",
@@ -63,6 +64,7 @@
     "@types/node": "^18.19.9",
     "@types/react": "^18",
     "@types/react-dom": "^18",
+    "@types/react-infinite-scroller": "^1.2.5",
     "@types/react-virtualized": "^9.21.8",
     "@typescript-eslint/eslint-plugin": "^7.4.0",
     "@typescript-eslint/parser": "^7.4.0",
diff --git a/ivette/src/frama-c/index.tsx b/ivette/src/frama-c/index.tsx
index 5e759842b4f30fa34f93884780214b18ec874c5f..33a5b74233eba561b64edf5bbdc5cf9aeea2496b 100644
--- a/ivette/src/frama-c/index.tsx
+++ b/ivette/src/frama-c/index.tsx
@@ -28,7 +28,7 @@ import React from 'react';
 import * as Ivette from 'ivette';
 
 import History from 'frama-c/kernel/History';
-import { Functions, Globals, Types } from 'frama-c/kernel/Globals';
+import Globals from 'frama-c/kernel/Globals';
 import ASTview from 'frama-c/kernel/ASTview';
 import ASTinfo from 'frama-c/kernel/ASTinfo';
 import SourceCode from 'frama-c/kernel/SourceCode';
@@ -50,11 +50,7 @@ Menu.init();
 Ivette.registerSidebar({
   id: 'fc.kernel.globals',
   label: 'AST',
-  children: <>
-    <Types />
-    <Globals />
-    <Functions />
-  </>
+  children: <Globals />
 });
 
 Ivette.registerToolbar({
diff --git a/ivette/src/frama-c/kernel/Globals.tsx b/ivette/src/frama-c/kernel/Globals.tsx
index 53dc1942357f644d2dba65c21c43eda6116a4cd9..d2f52cf0a35ab36310feba36c24a3916b7f91b25 100644
--- a/ivette/src/frama-c/kernel/Globals.tsx
+++ b/ivette/src/frama-c/kernel/Globals.tsx
@@ -24,7 +24,7 @@
 // --- Frama-C Globals
 // --------------------------------------------------------------------------
 
-import React, { ReactNode } from 'react';
+import React from 'react';
 import * as Dome from 'dome';
 import * as Json from 'dome/data/json';
 import { classes } from 'dome/misc/utils';
@@ -32,6 +32,7 @@ import { alpha } from 'dome/data/compare';
 import { Section, Item } from 'dome/frame/sidebars';
 import { Button } from 'dome/controls/buttons';
 import { Label } from 'dome/controls/labels';
+import InfiniteScroll from 'react-infinite-scroller';
 
 import * as Ivette from 'ivette';
 import * as Server from 'frama-c/server';
@@ -41,6 +42,7 @@ import * as Locations from 'frama-c/kernel/Locations';
 import { computationState } from 'frama-c/plugins/eva/api/general';
 import * as Eva from 'frama-c/plugins/eva/api/general';
 
+
 // --------------------------------------------------------------------------
 // --- Global Search Hints
 // --------------------------------------------------------------------------
@@ -95,21 +97,22 @@ function menuItem(label: string, [b, flip]: setting, enabled?: boolean)
 // --- Lists
 // --------------------------------------------------------------------------
 
-interface ListProps {
+interface InfiniteScrollableListProps {
+  scrollableParent: React.RefObject<HTMLDivElement>;
+}
+
+type ListProps = {
   name: string;
   total: number;
   filteringMenuItems: Dome.PopupMenuItem[];
   children: JSX.Element[];
-}
+} & InfiniteScrollableListProps
 
 function List(props: ListProps): JSX.Element {
-  const { name, total, filteringMenuItems, children } = props;
+  const [displayedCount, setDisplayedCount] = React.useState(100);
+  const { name, total, filteringMenuItems, children, scrollableParent } = props;
   const Name = name.charAt(0).toUpperCase() + name.slice(1);
   const count = children.length;
-  const [slice, setSlice] = React.useState(1500);
-  React.useEffect(() => {
-    if (count < slice) setSlice(1500);
-  }, [count]);
 
   const filterButtonProps = {
     icon: 'TUNINGS',
@@ -117,34 +120,38 @@ function List(props: ListProps): JSX.Element {
     onClick: () => Dome.popupMenu(filteringMenuItems),
   };
 
-  const noItems =
-    <div className='dome-xSideBarSection-content'>
-      <label className='globals-info'>
-        There is no {name} to display.
-      </label>
-    </div>;
-
-  const allFiltered =
-    <div className='dome-xSideBarSection-content'>
-      <label className='globals-info'>
-        All {name}s are filtered. Try adjusting {name} filters.
-      </label>
-      <Button {...filterButtonProps} label={`${Name}s filters`} />
-    </div>;
-
-  const omittedItems =
-    <div className='dome-xSideBarSection-content'>
-      <label className='globals-info'>
-        ({count - slice} omitted)
-      </label>
-      <Button
-        icon='CIRC.PLUS'
-        label="Show more"
-        onClick={() => setSlice(slice+500)}
-      />
-    </div>;
-
-  const items = count > slice ? children.slice(0, slice) : children;
+  let contents;
+
+  if (count <= 0) {
+    contents =
+      <div className='dome-xSideBarSection-content'>
+        <label className='globals-info'>
+          All {name}s are filtered. Try adjusting {name} filters.
+        </label>
+        <Button {...filterButtonProps} label={`${Name}s filters`} />
+      </div>;
+  }
+  else if (total <= 0) {
+    contents =
+      <div className='dome-xSideBarSection-content'>
+        <label className='globals-info'>
+          There is no {name} to display.
+        </label>
+      </div>;
+  }
+  else {
+    contents =
+      <InfiniteScroll
+        pageStart={0}
+        loadMore={() => setDisplayedCount(displayedCount + 100)}
+        hasMore={displayedCount < count}
+        loader={<Label key={-1}>Loading more...</Label>}
+        useWindow={false}
+        getScrollParent={() => scrollableParent.current}
+      >
+        {children.slice(0, displayedCount)}
+      </InfiniteScroll>;
+  }
 
   return (
     <Section
@@ -156,8 +163,7 @@ function List(props: ListProps): JSX.Element {
       summary={[count]}
       className='globals-section'
     >
-      {count > 0 ? items : total > 0 ? allFiltered : noItems}
-      {children.length > 1500 ? omittedItems : null}
+      {contents}
     </Section>
   );
 }
@@ -216,7 +222,9 @@ function computeFcts(
   return arr.sort((f, g) => alpha(f.name, g.name));
 }
 
-export function Functions(): JSX.Element {
+type FunctionProps = InfiniteScrollableListProps
+
+export function Functions(props: FunctionProps): JSX.Element {
 
   // Hooks
   const scope = States.useCurrentScope();
@@ -287,11 +295,6 @@ export function Functions(): JSX.Element {
     menuItem('Selected only', selected, multipleSelectionActive),
   ];
 
-  // Truncated
-  const allFunctions =
-    fcts.length > 1500 ? fcts.slice(0, 1500) : fcts;
-  const omitted = fcts.length - 1500;
-
   // Filtered
   const items =
     fcts
@@ -303,6 +306,7 @@ export function Functions(): JSX.Element {
       name="function"
       total={fcts.length}
       filteringMenuItems={contextMenuItems}
+      scrollableParent={props.scrollableParent}
     >
       {items}
     </List>
@@ -329,7 +333,9 @@ function makeVarItem(
   );
 }
 
-export function Globals(): JSX.Element {
+type VariablesProps = InfiniteScrollableListProps
+
+export function Variables(props: VariablesProps): JSX.Element {
 
   // Hooks
   const scope = States.useCurrentScope();
@@ -399,6 +405,7 @@ export function Globals(): JSX.Element {
       name="variable"
       total={variables.length}
       filteringMenuItems={contextMenuItems}
+      scrollableParent={props.scrollableParent}
     >
       {items}
     </List>
@@ -488,3 +495,18 @@ export function Types(): JSX.Element {
 }
 
 // --------------------------------------------------------------------------
+// --- All globals
+// --------------------------------------------------------------------------
+
+export default function Globals(): JSX.Element {
+  const scrollableArea = React.useRef<HTMLDivElement>(null);
+  return (
+    <div ref={scrollableArea} className="globals-scrollable-area">
+      <Types />
+      <Variables scrollableParent={scrollableArea} />
+      <Functions scrollableParent={scrollableArea} />
+    </div>
+  );
+}
+
+// --------------------------------------------------------------------------
diff --git a/ivette/src/frama-c/kernel/style.css b/ivette/src/frama-c/kernel/style.css
index d9e59c1d7b91c05ddc8f2e7d7a83d87b8b4e8f20..db351090b3fe8f2132e0ee0593be75505b230d35 100644
--- a/ivette/src/frama-c/kernel/style.css
+++ b/ivette/src/frama-c/kernel/style.css
@@ -64,6 +64,13 @@
 /* --- Globals                                                            --- */
 /* -------------------------------------------------------------------------- */
 
+.globals-scrollable-area {
+    width: 100%;
+    height: 100%;
+    overflow-x: hidden;
+    overflow-y: scroll;
+}
+
 .globals-info {
     color: var(--info-text-discrete);
     font-style: italic;
diff --git a/ivette/yarn.lock b/ivette/yarn.lock
index 3637da3ac4476d9cf8d32b7b114fbd1da752c629..dff0d728be9d1aea58b9a657bd1bb6d6a7f3a1dd 100644
--- a/ivette/yarn.lock
+++ b/ivette/yarn.lock
@@ -984,6 +984,13 @@
   dependencies:
     "@types/react" "*"
 
+"@types/react-infinite-scroller@^1.2.5":
+  version "1.2.5"
+  resolved "https://registry.yarnpkg.com/@types/react-infinite-scroller/-/react-infinite-scroller-1.2.5.tgz#7c770be59465f3aaa1b86377d792d52de5e74047"
+  integrity sha512-fJU1jhMgoL6NJFrqTM0Ob7tnd2sQWGxe2ESwiU6FZWbJK/VO/Er5+AOhc+e2zbT0dk5pLygqctsulOLJ8xnSzw==
+  dependencies:
+    "@types/react" "*"
+
 "@types/react-virtualized@^9.21.8":
   version "9.21.29"
   resolved "https://registry.yarnpkg.com/@types/react-virtualized/-/react-virtualized-9.21.29.tgz#480b647f43a42f8e414d1af49a0ccd9b16537655"
@@ -4577,7 +4584,7 @@ promise-retry@^2.0.1:
     err-code "^2.0.2"
     retry "^0.12.0"
 
-prop-types@>=15.0.0, prop-types@^15.5.10, prop-types@^15.6.0, prop-types@^15.7.2, prop-types@^15.8.1:
+prop-types@>=15.0.0, prop-types@^15.5.10, prop-types@^15.5.8, prop-types@^15.6.0, prop-types@^15.7.2, prop-types@^15.8.1:
   version "15.8.1"
   resolved "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz"
   integrity sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==
@@ -4645,6 +4652,13 @@ react-fast-compare@^3.2.2:
   resolved "https://registry.yarnpkg.com/react-fast-compare/-/react-fast-compare-3.2.2.tgz#929a97a532304ce9fee4bcae44234f1ce2c21d49"
   integrity sha512-nsO+KSNgo1SbJqJEYRE9ERzo7YtYbou/OqjSQKxV7jcKox7+usiUVZOAC+XnDOABXggQTno0Y1CpVnuWEc1boQ==
 
+react-infinite-scroller@^1.2.6:
+  version "1.2.6"
+  resolved "https://registry.yarnpkg.com/react-infinite-scroller/-/react-infinite-scroller-1.2.6.tgz#8b80233226dc753a597a0eb52621247f49b15f18"
+  integrity sha512-mGdMyOD00YArJ1S1F3TVU9y4fGSfVVl6p5gh/Vt4u99CJOptfVu/q5V/Wlle72TMgYlBwIhbxK5wF0C/R33PXQ==
+  dependencies:
+    prop-types "^15.5.8"
+
 react-is@^16.13.1:
   version "16.13.1"
   resolved "https://registry.npmjs.org/react-is/-/react-is-16.13.1.tgz"