@@ -31,31 +31,32 @@ using namespace llvm;
3131 * create CFG
3232 * checkBeginning
333310:for all BB in CFG insert at beginning
34- 11: signature ← signature − subRanP revV al
34+ 11: signature ← signature − subRanPrevVal
353512: if signature != compileTimeSig error()
363613:for all BB in CFG do
3737 * checkRetVal
383814: if Last Instr. is return instr. and NrIntrBB > 1 then
393915: Calculate needed variables
404016: return Val ← random number
41- 17: adjust Value ← (compile TimeSigBB + Sum{instrMonUpdates}) -
41+ 17: adjust Value ← (compileTimeSigBB + Sum{instrMonUpdates}) -
424218: return Val
434319: Insert signature update before return instr.
444420: signature ← signature + adjustValue
454521: if signature != returnVal error()
464622: else
4747 * checkJump
484823: for all Successor of BB do
49- 24: adjust Value ← (compile TimeSigBB + \Sum{instrMonUpdates}) -
50- 25: (compile TimeSigsuccs + subRanPrevValsuccs )
49+ 24: adjustValue ← (compileTimeSigBB + \Sum{instrMonUpdates}) -
50+ 25: (compileTimeSigsuccs + subRanPrevValsuccs)
515126: Insert signature update at BB end
52- 27: signature ← signature + adjust Value
52+ 27: signature ← signature + adjustValue
5353*/
5454
5555
5656// --- INITIALIZE BLOCKS RANDOM ---
5757
58- bool isNotUniqueCompileTimeSig (int bb_num,
58+ bool isNotUniqueCompileTimeSig (
59+ const int bb_num,
5960 const std::unordered_map<BasicBlock*, int > &compileTimeSig
6061) {
6162 for (const auto &pair : compileTimeSig) {
@@ -64,7 +65,7 @@ bool isNotUniqueCompileTimeSig(int bb_num,
6465 return false ;
6566}
6667
67- bool unicity (
68+ bool isNotUnique (
6869 const int bb_num, const int subrun_num,
6970 const std::unordered_map<BasicBlock*, int > &RandomNumBBs,
7071 const std::unordered_map<BasicBlock*, int > &SubRanPrevVals
@@ -88,17 +89,20 @@ void RACFED::initializeBlocksSignatures(Module &Md) {
8889 for (Function &Fn : Md) {
8990 if (shouldCompile (Fn, FuncAnnotations)) {
9091 for (BasicBlock &BB : Fn) {
92+
9193 do {
9294 randomBB = rand ();
9395 } while (isNotUniqueCompileTimeSig (randomBB, compileTimeSig));
9496
9597 do {
9698 randomSub = rand ();
97- } while (unicity (i, randomSub, compileTimeSig, subRanPrevVals));
99+ } while (isNotUnique (i, randomSub, compileTimeSig, subRanPrevVals));
100+
98101 compileTimeSig.insert (std::pair (&BB, randomBB));// not random, guarantees unicity
99102 subRanPrevVals.insert (std::pair (&BB, randomSub)); // In this way the sub value is random
100103 sumIntraInstruction.insert (std::pair (&BB, 0 ));// assign value to the sum of the instr
101104 i++;
105+
102106 }
103107 }
104108 }
@@ -116,27 +120,13 @@ void originalInstruction(BasicBlock &BB, std::vector<Instruction*> &OrigInstruc
116120 }
117121}
118122
119- int countOriginalInstructions (BasicBlock &BB) {
120- int count = 0 ;
121- for (Instruction &I : BB) {
122- if (isa<PHINode>(&I)) continue ; // NON è originale
123- if (I.isTerminator ()) continue ; // NON è originale
124- if (isa<DbgInfoIntrinsic>(&I)) continue ; // debug, ignora
125- count++;
126- }
127- return count;
128- }
129-
130123void RACFED::updateCompileSigRandom (Function &F, Module &Md) {
131124 LLVMContext &Ctx = Md.getContext ();
132125 GlobalVariable *SigGV = Md.getNamedGlobal (" signature" );
133126 std::mt19937 rng (0xC0FFEE ); // seed fisso per riproducibilità
134127 std::uniform_int_distribution<uint32_t > dist (1 , 0x7fffffff );
135128 auto *I32 = Type::getInt32Ty (Ctx);
136129 if (!SigGV) {
137- #if MARTI_DEBUG
138- errs () << " SigGV " << SigGV << " \n " ;
139- #endif
140130 SigGV = new GlobalVariable (
141131 Md,
142132 I32,
@@ -146,19 +136,18 @@ void RACFED::updateCompileSigRandom(Function &F, Module &Md) {
146136 " signature" );
147137 }
148138
149- bool changed = false ;
150-
151139 for (auto &BB: F){
152140 std::vector<Instruction*> OrigInstructions;
153141 originalInstruction (BB, OrigInstructions);
154142
155143 if (OrigInstructions.size () <= 2 )
156144 continue ;
157145
146+ uint64_t partial_sum;
147+
158148 for (Instruction *I : OrigInstructions) {
159149 Instruction *InsertPt = nullptr ;
160150
161-
162151 // Non puoi inserire "dopo" un terminator: inserisci prima del terminator stesso
163152 if (I->isTerminator ()) {
164153 InsertPt = I; // insert BEFORE terminator
@@ -170,77 +159,41 @@ void RACFED::updateCompileSigRandom(Function &F, Module &Md) {
170159
171160 // signature = signature + randomConstant
172161 uint32_t K = dist (rng);
173- #if MARTI_DEBUG
174- errs () << " Dist value: " << K << " \n " ;
175- #endif
162+
163+ try {
164+ partial_sum = K + sumIntraInstruction.at (&BB);
165+ } catch (std::out_of_range &) {
166+ partial_sum = K;
167+ }
168+
169+ sumIntraInstruction.insert (std::pair (&BB, partial_sum));
170+
176171 Value *OldSig = B.CreateLoad (I32, SigGV);
177- #if MARTI_DEBUG
178- errs () << " Loaded Signature" << " \n " ;
179- #endif
180172 Value *Add = B.CreateAdd (OldSig, ConstantInt::get (I32, K), " sig_add" );
181173 B.CreateStore (Add, SigGV);
182- changed= true ;
183174 }
184175 }
185176}
186177
187178// --- CREATE CFG VERIFICATION ---
188179
189180
190- void RACFED::splitBBsAtCalls (Module &Md) {
191- for (Function &Fn : Md) {
192- if (shouldCompile (Fn, FuncAnnotations)) {
193- std::vector<CallBase *> CallInsts;
194- for (BasicBlock &BB : Fn) {
195- for (Instruction &I : BB) {
196- if (isa<CallBase>(&I) && !isa<IntrinsicInst>(&I)) {
197- CallInsts.push_back (cast<CallBase>(&I));
198- }
199- }
200- }
201-
202- for (CallBase *Call : CallInsts) {
203- if (Call->getParent ()->getTerminator () != Call) {
204- SplitBlock (Call->getParent (), Call->getNextNode ());
205- }
206- }
207- }
208- }
209- }
210-
211- CallBase *RACFED::isCallBB (BasicBlock &BB) {
212- for (Instruction &I : BB) {
213- if (isa<CallBase>(&I) && !isa<IntrinsicInst>(&I)) {
214- return cast<CallBase>(&I);
215- }
216- }
217- return nullptr ;
218- }
219-
220- void RACFED::initializeEntryBlocksMap (Module &Md) {
221- // Implementation for INTRA_FUNCTION_CFC == 1, left empty for now as we
222- // default to 0
223- }
224-
225- Value *RACFED::getCondition (Instruction &I) {
226- // Helper to get condition from terminator if it's a branch
227- if (BranchInst *BI = dyn_cast<BranchInst>(&I)) {
228- if (BI->isConditional ()) {
229- return BI->getCondition ();
230- }
231- }
232- return nullptr ;
233- }
234181
235182void RACFED::createCFGVerificationBB (
236183 BasicBlock &BB, std::unordered_map<BasicBlock *, int > &RandomNumberBBs,
237184 std::unordered_map<BasicBlock *, int > &SubRanPrevVals, Value &RuntimeSig,
238- Value &RetSig, BasicBlock &ErrBB) {
185+ Value &RetSig, BasicBlock &ErrBB
186+ ) {
187+
188+ // checkBeginning() NON ENTRY BLOCK
189+ // compileTimeSig - subRunPrevVal
190+ // if compileTimeSig != runtime_sig error()
239191
240192 auto *IntType = llvm::Type::getInt32Ty (BB.getContext ());
241193
242194 int randomNumberBB = RandomNumberBBs.find (&BB)->second ;
243195 int subRanPrevVal = SubRanPrevVals.find (&BB)->second ;
196+
244197 // in this case BB is not the first Basic Block of the function, so it has to
245198 // update RuntimeSig and check it
246199 if (!BB.isEntryBlock ()) {
@@ -286,6 +239,16 @@ void RACFED::createCFGVerificationBB(
286239 }
287240 }
288241
242+ // checkReturnVal()
243+ // compute returnValue
244+ // compute adjValue
245+ // runtime_sig = runtime_sig + adjValue
246+
247+
248+ // checkBranchJump()
249+ // compute adjValue
250+ // runtime_sig = runtime_sig + adjValue
251+
289252 // update the signature for the successors
290253 int randomNumberBB_succ;
291254 int subRanPrevVal_succ;
@@ -327,27 +290,27 @@ void RACFED::createCFGVerificationBB(
327290 }
328291
329292 // Handle return instructions
330- if (isa<ReturnInst>(Term)) {
331- BasicBlock *RetVerificationBB = BasicBlock::Create (
332- BB.getContext (), " RACFED_ret_Verification_BB" , BB.getParent (), &BB);
333- // Move instructions from BB to RetVerificationBB, except the verification
334- // logic we just added? No, we want to verify BEFORE return. Actually, the
335- // verification block is already added at the beginning of BB. Now we want
336- // to update signature before return? RASM updates signature at exit?
337-
338-
339-
340- IRBuilder<> BRet (RetVerificationBB);
341- Value *InstrRuntimeSig = BRet.CreateLoad (IntType, &RuntimeSig, true );
342- Value *InstrRetSig = BRet.CreateLoad (IntType, &RetSig, true );
343-
344- // In RASM/RACFED, we might check if RuntimeSig matches RetSig (or some
345- // derived value) at return. For now, let's just check if they are
346- // consistent. But RetSig is initialized to RandomNumberBBs.size() +
347- // currSig.
348-
349- // Let's stick to the basic block verification for now.
350- }
293+ // if (isa<ReturnInst>(Term)) {
294+ // BasicBlock *RetVerificationBB = BasicBlock::Create(
295+ // BB.getContext(), "RACFED_ret_Verification_BB", BB.getParent(), &BB);
296+ // // Move instructions from BB to RetVerificationBB, except the verification
297+ // // logic we just added? No, we want to verify BEFORE return. Actually, the
298+ // // verification block is already added at the beginning of BB. Now we want
299+ // // to update signature before return? RASM updates signature at exit?
300+ //
301+ //
302+ //
303+ // IRBuilder<> BRet(RetVerificationBB);
304+ // Value *InstrRuntimeSig = BRet.CreateLoad(IntType, &RuntimeSig, true);
305+ // Value *InstrRetSig = BRet.CreateLoad(IntType, &RetSig, true);
306+ //
307+ // // In RASM/RACFED, we might check if RuntimeSig matches RetSig (or some
308+ // // derived value) at return. For now, let's just check if they are
309+ // // consistent. But RetSig is initialized to RandomNumberBBs.size() +
310+ // // currSig.
311+ //
312+ // // Let's stick to the basic block verification for now.
313+ // }
351314}
352315
353316PreservedAnalyses RACFED::run (Module &Md, ModuleAnalysisManager &AM) {
@@ -380,28 +343,10 @@ PreservedAnalyses RACFED::run(Module &Md, ModuleAnalysisManager &AM) {
380343 // break;
381344 // }
382345 // }
383- //
384- // for (BasicBlock &BB : Fn) {
385- // std::vector<Instruction*> OrigInstructions;
386- // originalInstruction(BB, OrigInstructions);
387- // if (OrigInstructions.size()<2)
388- // continue;
389- // int sumOfIntraUpdates = 0;
390- // auto *IntType = llvm::Type::getInt32Ty(BB.getContext()); // control to get context for add and compare ...
391- //
392- // for (Instruction *I:OrigInstructions) {
393- // int r = rand();
394- // sumOfIntraUpdates += r;
395- // InstrUpdates[I]=r;
396- // }
397- // sumIntraInstruction[&BB] = sumOfIntraUpdates;
398- // }
399346 // }
400347 return PreservedAnalyses::all ();
401348}
402349
403-
404-
405350extern " C" ::llvm::PassPluginLibraryInfo LLVM_ATTRIBUTE_WEAK
406351
407352llvmGetPassPluginInfo () {
@@ -417,3 +362,50 @@ llvmGetPassPluginInfo() {
417362 });
418363 }};
419364}
365+
366+ // -- UNUSED FUNCTIONS --
367+
368+ // void RACFED::splitBBsAtCalls(Module &Md) {
369+ // for (Function &Fn : Md) {
370+ // if (shouldCompile(Fn, FuncAnnotations)) {
371+ // std::vector<CallBase *> CallInsts;
372+ // for (BasicBlock &BB : Fn) {
373+ // for (Instruction &I : BB) {
374+ // if (isa<CallBase>(&I) && !isa<IntrinsicInst>(&I)) {
375+ // CallInsts.push_back(cast<CallBase>(&I));
376+ // }
377+ // }
378+ // }
379+ //
380+ // for (CallBase *Call : CallInsts) {
381+ // if (Call->getParent()->getTerminator() != Call) {
382+ // SplitBlock(Call->getParent(), Call->getNextNode());
383+ // }
384+ // }
385+ // }
386+ // }
387+ // }
388+ //
389+ // CallBase *RACFED::isCallBB(BasicBlock &BB) {
390+ // for (Instruction &I : BB) {
391+ // if (isa<CallBase>(&I) && !isa<IntrinsicInst>(&I)) {
392+ // return cast<CallBase>(&I);
393+ // }
394+ // }
395+ // return nullptr;
396+ // }
397+ //
398+ // void RACFED::initializeEntryBlocksMap(Module &Md) {
399+ // // Implementation for INTRA_FUNCTION_CFC == 1, left empty for now as we
400+ // // default to 0
401+ // }
402+ //
403+ // Value *RACFED::getCondition(Instruction &I) {
404+ // // Helper to get condition from terminator if it's a branch
405+ // if (BranchInst *BI = dyn_cast<BranchInst>(&I)) {
406+ // if (BI->isConditional()) {
407+ // return BI->getCondition();
408+ // }
409+ // }
410+ // return nullptr;
411+ // }
0 commit comments