diff --git a/package-lock.json b/package-lock.json
index 4444de29a715c5abccb6351afde6e97dd2a96c96..00f2081bcfdf7d63fc7301f534af8309da642912 100644
Binary files a/package-lock.json and b/package-lock.json differ
diff --git a/src/mol-model-formats/structure/mmcif/atomic.ts b/src/mol-model-formats/structure/mmcif/atomic.ts
index b43be7fe712175330a35626d2840383eda44e77b..38e39f5b63ad2108e61d1f1cbadac5e78b21154c 100644
--- a/src/mol-model-formats/structure/mmcif/atomic.ts
+++ b/src/mol-model-formats/structure/mmcif/atomic.ts
@@ -16,11 +16,8 @@ import { ElementSymbol } from 'mol-model/structure/model/types';
 import { Entities } from 'mol-model/structure/model/properties/common';
 import { getAtomicRanges } from 'mol-model/structure/model/properties/utils/atomic-ranges';
 import { getAtomicDerivedData } from 'mol-model/structure/model/properties/utils/atomic-derived';
-import { ModelFormat } from '../format';
-import mmCIF_Format = ModelFormat.mmCIF
 import { FormatData } from './parser';
 
-
 type AtomSite = mmCIF_Database['atom_site']
 
 function findHierarchyOffsets(atom_site: AtomSite) {
@@ -45,13 +42,14 @@ function findHierarchyOffsets(atom_site: AtomSite) {
     return { residues, chains };
 }
 
-function createHierarchyData(atom_site: AtomSite, offsets: { residues: ArrayLike<number>, chains: ArrayLike<number> }): AtomicData {
+function createHierarchyData(atom_site: AtomSite, sourceIndex: Column<number>, offsets: { residues: ArrayLike<number>, chains: ArrayLike<number> }): AtomicData {
     const atoms = Table.ofColumns(AtomsSchema, {
         type_symbol: Column.ofArray({ array: Column.mapToArray(atom_site.type_symbol, ElementSymbol), schema: Column.Schema.Aliased<ElementSymbol>(Column.Schema.str) }),
         label_atom_id: atom_site.label_atom_id,
         auth_atom_id: atom_site.auth_atom_id,
         label_alt_id: atom_site.label_alt_id,
-        pdbx_formal_charge: atom_site.pdbx_formal_charge
+        pdbx_formal_charge: atom_site.pdbx_formal_charge,
+        sourceIndex
     });
     const residues = Table.view(atom_site, ResiduesSchema, offsets.residues);
     // Optimize the numeric columns
@@ -80,9 +78,9 @@ function isHierarchyDataEqual(a: AtomicData, b: AtomicData) {
         && Table.areEqual(a.atoms as Table<AtomsSchema>, b.atoms as Table<AtomsSchema>)
 }
 
-export function getAtomicHierarchyAndConformation(format: mmCIF_Format, atom_site: AtomSite, entities: Entities, formatData: FormatData, previous?: Model) {
+export function getAtomicHierarchyAndConformation(atom_site: AtomSite, sourceIndex: Column<number>, entities: Entities, formatData: FormatData, previous?: Model) {
     const hierarchyOffsets = findHierarchyOffsets(atom_site);
-    const hierarchyData = createHierarchyData(atom_site, hierarchyOffsets);
+    const hierarchyData = createHierarchyData(atom_site, sourceIndex, hierarchyOffsets);
 
     if (previous && isHierarchyDataEqual(previous.atomicHierarchy, hierarchyData)) {
         return {
diff --git a/src/mol-model-formats/structure/mmcif/ihm.ts b/src/mol-model-formats/structure/mmcif/ihm.ts
index 731af9e3af83de9784c51bba90da32d0c15de777..405fec8cf0fab7b019f477e41ac0dea1d61a9716 100644
--- a/src/mol-model-formats/structure/mmcif/ihm.ts
+++ b/src/mol-model-formats/structure/mmcif/ihm.ts
@@ -21,6 +21,7 @@ export interface IHMData {
     model_name: string,
     entities: Entities,
     atom_site: mmCIF['atom_site'],
+    atom_site_sourceIndex: Column<number>,
     ihm_sphere_obj_site: mmCIF['ihm_sphere_obj_site'],
     ihm_gaussian_obj_site: mmCIF['ihm_gaussian_obj_site']
 }
diff --git a/src/mol-model-formats/structure/mmcif/parser.ts b/src/mol-model-formats/structure/mmcif/parser.ts
index 17d4f3a5b5fa0f92dbf1d1965d314c0256fe2418..44835f9e96254479326925d00c25bc863ce7363a 100644
--- a/src/mol-model-formats/structure/mmcif/parser.ts
+++ b/src/mol-model-formats/structure/mmcif/parser.ts
@@ -169,8 +169,8 @@ function getFormatData(format: mmCIF_Format): FormatData {
     }
 }
 
-function createStandardModel(format: mmCIF_Format, atom_site: AtomSite, entities: Entities, formatData: FormatData, previous?: Model): Model {
-    const atomic = getAtomicHierarchyAndConformation(format, atom_site, entities, formatData, previous);
+function createStandardModel(format: mmCIF_Format, atom_site: AtomSite, sourceIndex: Column<number>, entities: Entities, formatData: FormatData, previous?: Model): Model {
+    const atomic = getAtomicHierarchyAndConformation(atom_site, sourceIndex, entities, formatData, previous);
     if (previous && atomic.sameAsPrevious) {
         return {
             ...previous,
@@ -209,7 +209,7 @@ function createStandardModel(format: mmCIF_Format, atom_site: AtomSite, entities
 }
 
 function createModelIHM(format: mmCIF_Format, data: IHMData, formatData: FormatData): Model {
-    const atomic = getAtomicHierarchyAndConformation(format, data.atom_site, data.entities, formatData);
+    const atomic = getAtomicHierarchyAndConformation(data.atom_site, data.atom_site_sourceIndex, data.entities, formatData);
     const coarse = getIHMCoarse(data, formatData);
 
     return {
@@ -255,8 +255,8 @@ async function readStandard(ctx: RuntimeContext, format: mmCIF_Format, formatDat
     let modelStart = 0;
     while (modelStart < atomCount) {
         const modelEnd = findModelEnd(format.data.atom_site.pdbx_PDB_model_num, modelStart);
-        const atom_site = await sortAtomSite(ctx, format.data.atom_site, modelStart, modelEnd);
-        const model = createStandardModel(format, atom_site, entities, formatData, models.length > 0 ? models[models.length - 1] : void 0);
+        const { atom_site, sourceIndex } = await sortAtomSite(ctx, format.data.atom_site, modelStart, modelEnd);
+        const model = createStandardModel(format, atom_site, sourceIndex, entities, formatData, models.length > 0 ? models[models.length - 1] : void 0);
         attachProps(model);
         models.push(model);
         modelStart = modelEnd;
@@ -265,14 +265,17 @@ async function readStandard(ctx: RuntimeContext, format: mmCIF_Format, formatDat
 }
 
 function splitTable<T extends Table<any>>(table: T, col: Column<number>) {
-    const ret = new Map<number, T>()
+    const ret = new Map<number, { table: T, start: number, end: number }>()
     const rowCount = table._rowCount;
     let modelStart = 0;
     while (modelStart < rowCount) {
         const modelEnd = findModelEnd(col, modelStart);
         const id = col.value(modelStart);
-        const window = Table.window(table, table._schema, modelStart, modelEnd) as T;
-        ret.set(id, window);
+        ret.set(id, {
+            table: Table.window(table, table._schema, modelStart, modelEnd) as T,
+            start: modelStart,
+            end: modelEnd
+        });
         modelStart = modelEnd;
     }
     return ret;
@@ -286,8 +289,9 @@ async function readIHM(ctx: RuntimeContext, format: mmCIF_Format, formatData: Fo
         throw new Error('expected _atom_site.ihm_model_id to be defined')
     }
 
-    // TODO: will IHM require sorting or will we trust it?
     const atom_sites = splitTable(format.data.atom_site, format.data.atom_site.ihm_model_id);
+    // TODO: will coarse IHM records require sorting or will we trust it?
+    // ==> Probably implement a sort as as well and store the sourceIndex same as with atomSite
     const sphere_sites = splitTable(format.data.ihm_sphere_obj_site, format.data.ihm_sphere_obj_site.model_id);
     const gauss_sites = splitTable(format.data.ihm_gaussian_obj_site, format.data.ihm_gaussian_obj_site.model_id);
 
@@ -296,13 +300,26 @@ async function readIHM(ctx: RuntimeContext, format: mmCIF_Format, formatData: Fo
     const { model_id, model_name } = ihm_model_list;
     for (let i = 0; i < ihm_model_list._rowCount; i++) {
         const id = model_id.value(i);
+
+        let atom_site, atom_site_sourceIndex;
+        if (atom_sites.has(id)) {
+            const e = atom_sites.get(id)!;
+            const { atom_site: sorted, sourceIndex } = await sortAtomSite(ctx, e.table, e.start, e.end);
+            atom_site = sorted;
+            atom_site_sourceIndex = sourceIndex;
+        } else {
+            atom_site = Table.window(format.data.atom_site, format.data.atom_site._schema, 0, 0);
+            atom_site_sourceIndex = Column.ofIntArray([]);
+        }
+
         const data: IHMData = {
             model_id: id,
             model_name: model_name.value(i),
             entities: entities,
-            atom_site: atom_sites.has(id) ? atom_sites.get(id)! : Table.window(format.data.atom_site, format.data.atom_site._schema, 0, 0),
-            ihm_sphere_obj_site: sphere_sites.has(id) ? sphere_sites.get(id)! : Table.window(format.data.ihm_sphere_obj_site, format.data.ihm_sphere_obj_site._schema, 0, 0),
-            ihm_gaussian_obj_site: gauss_sites.has(id) ? gauss_sites.get(id)! : Table.window(format.data.ihm_gaussian_obj_site, format.data.ihm_gaussian_obj_site._schema, 0, 0)
+            atom_site,
+            atom_site_sourceIndex,
+            ihm_sphere_obj_site: sphere_sites.has(id) ? sphere_sites.get(id)!.table : Table.window(format.data.ihm_sphere_obj_site, format.data.ihm_sphere_obj_site._schema, 0, 0),
+            ihm_gaussian_obj_site: gauss_sites.has(id) ? gauss_sites.get(id)!.table : Table.window(format.data.ihm_gaussian_obj_site, format.data.ihm_gaussian_obj_site._schema, 0, 0)
         };
         const model = createModelIHM(format, data, formatData);
         attachProps(model);
diff --git a/src/mol-model-formats/structure/mmcif/sort.ts b/src/mol-model-formats/structure/mmcif/sort.ts
index 7cbee9e5b102854bb2c80120fbc4fbfe2baa57bf..868cd5dd86bed2dfb063a042a224fb54191ed52b 100644
--- a/src/mol-model-formats/structure/mmcif/sort.ts
+++ b/src/mol-model-formats/structure/mmcif/sort.ts
@@ -9,6 +9,8 @@ import { createRangeArray, makeBuckets } from 'mol-data/util';
 import { Column, Table } from 'mol-data/db';
 import { RuntimeContext } from 'mol-task';
 
+export type SortedAtomSite = mmCIF_Database['atom_site'] & { sourceIndex: Column<number> }
+
 function isIdentity(xs: ArrayLike<number>) {
     for (let i = 0, _i = xs.length; i < _i; i++) {
         if (xs[i] !== i) return false;
@@ -36,8 +38,11 @@ export async function sortAtomSite(ctx: RuntimeContext, atom_site: mmCIF_Databas
     }
 
     if (isIdentity(indices) && indices.length === atom_site._rowCount) {
-        return atom_site;
+        return { atom_site, sourceIndex: Column.ofIntArray(indices) };
     }
 
-    return Table.view(atom_site, atom_site._schema, indices) as mmCIF_Database['atom_site'];
+    return {
+        atom_site: Table.view(atom_site, atom_site._schema, indices) as mmCIF_Database['atom_site'],
+        sourceIndex: Column.ofIntArray(indices)
+    };
 }
\ No newline at end of file
diff --git a/src/mol-model/structure/model/properties/atomic/hierarchy.ts b/src/mol-model/structure/model/properties/atomic/hierarchy.ts
index 33c5993245ff39f69f73a5baf4a1e8dbb3a08c45..7262fe28a3d88264f02cb185cd580d8eb1d09fee 100644
--- a/src/mol-model/structure/model/properties/atomic/hierarchy.ts
+++ b/src/mol-model/structure/model/properties/atomic/hierarchy.ts
@@ -38,7 +38,14 @@ export const AtomsSchema = {
      * The net integer charge assigned to this atom.
      * This is the formal charge assignment normally found in chemical diagrams.
      */
-    pdbx_formal_charge: mmCIF.atom_site.pdbx_formal_charge
+    pdbx_formal_charge: mmCIF.atom_site.pdbx_formal_charge,
+
+    /**
+     * The index of this atom in the input data.
+     * Required because of sorting of atoms.
+     */
+    sourceIndex: Column.Schema.int
+
     // id, occupancy and B_iso_or_equiv are part of conformation
 };