3333#include < string>
3434#include < utility>
3535
36+ #include " ../vm/Print.h"
3637#include " ../vm/Symbols.h"
38+ #include " ../vm/Universe.h"
3739#include " ../vmobjects/VMClass.h"
3840#include " ../vmobjects/VMInvokable.h"
3941#include " ../vmobjects/VMPrimitive.h"
4042#include " ../vmobjects/VMSafePrimitive.h"
4143#include " ../vmobjects/VMSymbol.h"
44+ #include " /Users/smarr/Projects/SOM/SOMpp/src/vm/Print.h"
4245#include " Primitives.h"
4346
4447void PrimitiveContainer::Add (const char * name,
@@ -133,10 +136,12 @@ void PrimitiveContainer::Add(const char* name, bool classSide,
133136}
134137
135138template <class PrimT >
136- void PrimitiveContainer::installPrimitives (
139+ bool PrimitiveContainer::installPrimitives (
137140 bool classSide, bool showWarning, VMClass* clazz,
138141 std::map<std::string, std::pair<PrimT, PrimT>>& prims,
139142 VMInvokable* (*makePrimFn)(VMSymbol* sig, PrimT)) {
143+ bool hasHashMismatch = false ;
144+
140145 for (auto const & p : prims) {
141146 PrimT prim1 = std::get<0 >(p.second );
142147 PrimT prim2 = std::get<1 >(p.second );
@@ -150,27 +155,55 @@ void PrimitiveContainer::installPrimitives(
150155
151156 PrimInstallResult const result = clazz->InstallPrimitive (
152157 makePrimFn (sig, prim1), prim1.bytecodeHash , !prim2.IsValid ());
158+ if (!prim2.IsValid ()) {
159+ hasHashMismatch =
160+ hasHashMismatch || result == PrimInstallResult::HASH_MISMATCH;
161+ }
162+
153163 if (result == PrimInstallResult::INSTALLED_ADDED && showWarning) {
154164 cout << " Warn: Primitive " << p.first
155165 << " is not in class definition for class "
156166 << clazz->GetName ()->GetStdString () << ' \n ' ;
157167 } else if (result == PrimInstallResult::HASH_MISMATCH &&
158168 prim2.IsValid ()) {
159169 assert (prim1.isClassSide == prim2.isClassSide );
160- clazz->InstallPrimitive (makePrimFn (sig, prim2), prim2.bytecodeHash ,
161- true );
170+ PrimInstallResult const result2 = clazz->InstallPrimitive (
171+ makePrimFn (sig, prim2), prim2.bytecodeHash , true );
172+ hasHashMismatch =
173+ hasHashMismatch || result2 == PrimInstallResult::HASH_MISMATCH;
162174 }
163175 }
176+
177+ return hasHashMismatch;
164178}
165179
166180void PrimitiveContainer::InstallPrimitives (VMClass* clazz, bool classSide,
167181 bool showWarning) {
168- installPrimitives (classSide, showWarning, clazz, unaryPrims,
169- VMSafePrimitive::GetSafeUnary);
170- installPrimitives (classSide, showWarning, clazz, binaryPrims,
171- VMSafePrimitive::GetSafeBinary);
172- installPrimitives (classSide, showWarning, clazz, ternaryPrims,
173- VMSafePrimitive::GetSafeTernary);
174- installPrimitives (classSide, showWarning, clazz, framePrims,
175- VMPrimitive::GetFramePrim);
182+ bool hasHashMismatch = false ;
183+ hasHashMismatch =
184+ hasHashMismatch ||
185+ installPrimitives (classSide, showWarning, clazz, unaryPrims,
186+ VMSafePrimitive::GetSafeUnary);
187+ hasHashMismatch =
188+ hasHashMismatch ||
189+ installPrimitives (classSide, showWarning, clazz, binaryPrims,
190+ VMSafePrimitive::GetSafeBinary);
191+ hasHashMismatch =
192+ hasHashMismatch ||
193+ installPrimitives (classSide, showWarning, clazz, ternaryPrims,
194+ VMSafePrimitive::GetSafeTernary);
195+ hasHashMismatch = hasHashMismatch ||
196+ installPrimitives (classSide, showWarning, clazz,
197+ framePrims, VMPrimitive::GetFramePrim);
198+
199+ if (abortOnCoreLibHashMismatch && hasHashMismatch) {
200+ ErrorPrint (" The implementation of methods in " +
201+ clazz->GetName ()->GetStdString () +
202+ " seem to have changed.\n " );
203+ ErrorPrint (
204+ " The primitive implementation in the matching VM class may need to "
205+ " be changed. See for instance _Vector::_Vector() in "
206+ " primitives/Vector.cpp\n " );
207+ Quit (1 );
208+ }
176209}
0 commit comments