/// <summary> /// Load the complete assembled program /// Loads each file section of the program /// </summary> /// <param name="ar"></param> public CodeLabels(ArmAssembly.ArmAssembler ar) { _fileSections.Clear(); foreach (ArmAssembly.ArmFileInfo afi in ar.FileInfoTable) { _fileSections[afi.FileName] = new CodeFileLabels(); (_fileSections[afi.FileName] as CodeFileLabels).Load(afi); }//foreach }
/// <summary> /// Load a new program into the simulator. This function will compile it, load it and set up the /// simulator for a run. /// </summary> /// <param name="fileNames">list of filenames to load</param> /// <param name="preferences">ARMSim preferences</param> /// <returns>true if sucessful</returns> public bool Load(IList <string> fileNames) { this.ValidLoadedProgram = false; foreach (string str in fileNames) { if (str.EndsWith(".o") || str.EndsWith(".O")) { OutputConsoleString("Loading object code file {0}\n", str); } else if (str.EndsWith(".a") || str.EndsWith(".A")) { OutputConsoleString("Searching library archive {0}\n", str); } else { OutputConsoleString("Loading assembly language file {0}\n", str); } }//foreach mArmAssembler = new ArmAssembly.ArmAssembler(fileNames); try { //perform pass 1 on all the files mArmAssembler.PerformPass(); //ar.DumpInfo(); if (ArmAssembly.AssemblerErrors.ErrorReports.Count <= 0) { // now determine where everything will go in memory mArmAssembler.PlaceCode((int)this.ARMPreferences.SimulatorPreferences.MemoryStart); //ar.DumpInfo(); // allocate a block of memory for the assembled // and linked program mAssembledProgram = new ArmAssembly.AssembledProgram(mArmAssembler); // perform pass 2 on all the files mArmAssembler.PerformPass(mAssembledProgram); //ar.DumpInfo(); //ap.Hexdump(); // display all code } } catch (Exception ex) { OutputConsoleString("A fatal error occurred while assembling the program, Reason:{0}\n", ex.Message); OutputConsoleString("Please keep a copy of the ARM source code and report this ARMSim bug!\n"); return(false); }//catch if (ArmAssembly.AssemblerErrors.ErrorReports.Count > 0) { OutputConsoleString("The following assembler/loader errors occurred ...\n"); IDictionary <string, IList <ArmAssembly.ErrorReport> > xxx = ArmAssembly.AssemblerErrors.ErrorReports.ErrorLists; //display each reported error in the outputview foreach (string fileName in xxx.Keys) { OutputConsoleString("** File: {0}\n", fileName); IList <ArmAssembly.ErrorReport> ht = ArmAssembly.AssemblerErrors.ErrorReports.GetErrorsList(fileName); foreach (ArmAssembly.ErrorReport ce in ht) { string fmt; if (ce.Col == 0) { if (ce.Line == 0) { fmt = " Message = {0}\n"; } else { fmt = " Line {1}: Message = {0}\n"; } } else { fmt = " Line {1}, col {2}: Message = {0}\n"; } OutputConsoleString(fmt, ce.ErrorMsg, ce.Line, ce.Col); } } OutputConsoleString("End of assembler errors\n"); //all done for error case return(false); } //Construct the code labels data structure from the assembled program. mCodeLabels = new CodeLabels(mArmAssembler); //tell the simulator which directory to try for user files this.UserDirectory = System.IO.Path.GetDirectoryName(fileNames[0]); // set the program entry point to be the _start label if it exists; // otherwise set it to the address of main if it exists; // otherwise set it to the start of memory //save the entry point in case the user does a "Restart" but the preferences may have changed - dale if (!mCodeLabels.LabelToAddress("_start", ref mEntryPoint)) { if (!mCodeLabels.LabelToAddress("main", ref mEntryPoint)) { mEntryPoint = (uint)mAssembledProgram.StartAddress; } } //define the simulation memory //save the stack pointer in case the user does a "Restart" but the preferences may have changed - dale mStackPointer = this.DefineMemory(this.ARMPreferences.SimulatorPreferences, mAssembledProgram.Memory.Length); //create the caches based on the user preferences this.DefineCache(this.ARMPreferences.CachePreferences); //perform a restart - loads code into memory, zeros cpu registers, sets pc and sp //note sets the ValidLoadedProgram flag to true this.Restart(); return(true); }//Load