MODULE XoppcSystem; (** İ ProXon/ED 3.9.94 / 22.11.98 / 23.2.02 / 27.1.03 | *) (** Cross System Tool Box *) (* 3.1.05, AS USB support 27.1.05, UG ResetTarget changed, sitch off EECLK during download to minimize external noise 22.10.04, UG flash supported 23.1.03, ProXon/ED PROCEDURE TargetCmd *) IMPORT SYS := SYSTEM, Services, Log := StdLog, StdFolds, TextModels, TextMappers, DevCommanders, DevMarkers, Strings, Dialog, XU := XdeUtilities, Errors := XdeErrors, BDI := UsbBDI555, BDIMain := UsbBDI, CC := XoppcCompConsts, OPM := XoppcCompM, XE := XdeErrors, (*CRM := XoppcModules, *) OBJ := XoppcObjRefs, TMM := XoppcTargetMemAndMods, RegDict := XoppcTrgtRegDict, IMF := XoppcMemImageFile; (* constants and types *) CONST COMPARE_IMAGE = TRUE; CONST signOnMsg = "NTB Cross System MPC555 V 3.1.2 / 6.1.05"; errPrefix = "System_"; kernelModName = OBJ.kernelModName; configText = "TargetConfig.odc"; configHdrText = "TargetConfigHdr.odc"; ramImageFileName = "RAM.tim"; CONST nul = 0X; ht = 9X; false = 0; true = 1; newErr = 0; safetyZoneSize = 4*4; nofRegNamesPerLine = 8; nofRegNamesPerPage = 15; CONST classpath = "D:/work/USB/eclipse/mcdp/bin"; MAX_NOF_WORDS_FAST_DOWNLOAD = 101; CONST (*OPT Structure Forms (standard types) *) (* structure forms *) sfUndef = CC.sfUndef; sfSysByte = CC.sfSysByte; sfBool = CC.sfBool; sfShChar = CC.sfShChar; sfByte = CC.sfByte; sfShInt = CC.sfShInt; sfInt = CC.sfInt; sfShReal = CC.sfShReal; sfReal = CC.sfReal; sfSet = CC.sfSet; sfByteSet = CC.sfByteSet; sfShSet = CC.sfShSet; sfString = CC.sfString; sfNilTyp = CC.sfNilTyp; sfNoTyp = CC.sfNoTyp; sfPointer = CC.sfPointer; sfProcTyp = CC.sfProcTyp; sfComp = CC.sfComp; TYPE Name = OPM.Name; ShortName = ARRAY 16 OF CHAR; LongName = ARRAY 64 OF CHAR; ConstVarDesc = OBJ.ConstVarDesc; VarDesc = RECORD (ConstVarDesc) lname: LongName; textPos, ind: INTEGER END; SystemConstEntry = RECORD name: Name; val: INTEGER END; VAR Done-: BOOLEAN; (** previous operation successfully completed *) firstErr-, nofErrors-: SHORTINT; (** first error occured, see error list in CRErrors.Text *) promCodeSize-, ramCodeSize-, romModsVarSize-, ramModsVarSize- (* targVarSize- *): INTEGER; (** promCodeSize: size of code and constants of the set of target modules loaded to target RAM. ramCodeSize: size of code and constants of the set of target modules loaded to target RAM. targVarSize: size of all gloabal variables of the set of target modules defined by the parameter list of the Load command. Note: these variables may only be evaluated by the procedure DefineMemory of the module Target. Outside of the activation of this proc, the two vars are not valid. *) (* Variables *) itemNames: ARRAY 5 OF ARRAY 6 OF CHAR; formSizes: ARRAY sfComp + 1 OF SHORTINT; variables: ARRAY 8 OF VarDesc; nofVars: SHORTINT; tmpTargetInDebugMode: BOOLEAN; (* objRdr: OPM.ObjReader; referencePos: INTEGER; *) kernItemName: Name; (* refTextModel: TextModels.Model; refTextRdr: TextModels.Reader; refTextScnr: TextMappers.Scanner; *) gScnr: XU.Scanner; (* gloabal scanner *) gScnrBeg, gScnrEnd: INTEGER; targetCurrentAddr, targetMSR: INTEGER; CONST (* system table offsets *) CIsupStackOrg = 00H; CIstartAdr = 01H; CIsupStackSize = 02H; (*CImoduleTabBase=03H;*) CIcodeBaseRom = 04H; CIcodeSizeRom = 05H; CIcodeBaseRam = 06H; CIcodeSizeRam = 07H; CIramModsVarBase = 08H; CIramModsVarSize = 09H; CIsafetyZoneVH = 0AH; CIheapBase = 0CH; CIheapSize = 0DH; CIsafetyZoneHUS = 0EH; CIuserStackOrg = 10H; CIuserStackSize = 11H; CIsafetyZoneUSSS = 12H; CIsafetyZoneSSTop = 13H; CIsafetyZoneCode = 14H; (* 4 longs for safety zone codes *) CImaxNofModules = 1EH; CInofModules = 1FH; CIfirstModule = 20H; VAR (* target parameters, extracted from TobKernel and/or calculated by XoppcSystem *) systemParDefined, CwatchdogEnab: BOOLEAN; CromBase, CromSize, CramBase, CramSize: INTEGER; VcommandAdr: INTEGER; (* offset of system variable Vcommand in module TobKernel *) VAR kernelMemDeviceId: SHORTINT; configT: TextModels.Model; configTextForm: TextMappers.Formatter; VAR (* targget/host system parameters *) sysTab: POINTER TO ARRAY OF INTEGER; sysTabBase, sysTabSize, maxNofModules, vItagFcs: INTEGER; sysConsts: ARRAY 32 OF SystemConstEntry; nofSysConsts: INTEGER; anyCodeInReadOnly, anyCodeInRam: BOOLEAN; VAR Fcs: PROCEDURE (begin, end: INTEGER): SHORTINT; objText: TextModels.Model; objFrm: POINTER TO TextMappers.Formatter; VAR addrList*, dataList*: ARRAY 10000 OF INTEGER; maxDataListIndex*: INTEGER; (*---- debug primitives ---- (debugLog, dbgPT, dbgDetails) *) CONST debugLog = FALSE; (* FALSE, TRUE *) dbgPT = debugLog; (*procedure trace*) dbgDetails = dbgPT; (*trace details*) PROCEDURE DlLn ; BEGIN IF debugLog THEN Log.Ln END END DlLn; PROCEDURE DlTab ; BEGIN IF debugLog THEN Log.Tab END END DlTab; PROCEDURE DlChar (ch: CHAR); BEGIN IF debugLog THEN Log.Char(ch) END END DlChar; PROCEDURE DlString (IN str: ARRAY OF CHAR); BEGIN IF debugLog THEN Log.String(str) END END DlString; PROCEDURE DlStringLn (IN str: ARRAY OF CHAR); BEGIN IF debugLog THEN Log.String(str); Log.Ln END END DlStringLn; PROCEDURE DlHex (val: INTEGER); BEGIN IF debugLog THEN Log.Char('0'); Log.IntForm(val MOD 100000000L, Log.hexadecimal, 1, ' ', Log.hideBase); Log.Char('H') END END DlHex; PROCEDURE DlLHex (val: LONGINT); BEGIN IF debugLog THEN Log.IntForm(val, Log.hexadecimal, 1, ' ', Log.hideBase); Log.Char('H') END END DlLHex; PROCEDURE DlInt (val: INTEGER); BEGIN IF debugLog THEN Log.Int(val) END END DlInt; PROCEDURE DlLInt (val: LONGINT); BEGIN IF debugLog THEN Log.Int(val) END END DlLInt; PROCEDURE DlSet (val: SET); BEGIN IF debugLog THEN Log.Set(val) END END DlSet; PROCEDURE DlBool (val: BOOLEAN); BEGIN IF debugLog THEN Log.Bool(val) END END DlBool; PROCEDURE DlReal (val: REAL); BEGIN IF debugLog THEN Log.Real(val) END END DlReal; PROCEDURE DlBytes (bytes: ARRAY OF BYTE; len: INTEGER); VAR n: INTEGER; BEGIN IF debugLog THEN FOR n := 0 TO len - 1 DO DlTab; DlInt(bytes[n]) END END END DlBytes; (*---- end debug primitives ----*) PROCEDURE Error (errNr: SHORTINT); BEGIN IF Done THEN firstErr := errNr; Done := FALSE END; INC(nofErrors); XE.Error("", errPrefix, errNr, TRUE) END Error; PROCEDURE SyntaxErrorAtScnrPos (pos: INTEGER; errNr: SHORTINT); VAR errMsg: XU.String64; BEGIN IF Done THEN Strings.IntToString(errNr, errMsg); XE.GetErrorCommentByName(NIL, errPrefix + errMsg, errMsg); IF gScnr.sc.rider # NIL THEN DevMarkers.Insert(gScnr.Base(), pos, DevMarkers.dir.NewMsg(errMsg)); gScnr.SetPos(gScnr.Pos() + 1); END; Error(errNr); Log.String(" (lokate marker)"); Log.Ln END END SyntaxErrorAtScnrPos; PROCEDURE LogLine (s: ARRAY OF CHAR); BEGIN Log.String("XoppcSystem: "); Log.Tab; Log.String(s$); Log.Ln END LogLine; PROCEDURE LogInt (val: INTEGER); BEGIN Log.Int(val) END LogInt; PROCEDURE LogHex (val: INTEGER); BEGIN Log.Char('0'); Log.IntForm(val MOD 100000000L, Log.hexadecimal, 1, ' ', Log.hideBase); Log.Char('H') END LogHex; PROCEDURE LogCmdr; BEGIN Log.View(DevCommanders.dir.New()) END LogCmdr; PROCEDURE LogCmdrEnd; BEGIN Log.View(DevCommanders.dir.NewEnd()) END LogCmdrEnd; PROCEDURE LogSystemCmd (IN cmd: ARRAY OF CHAR); BEGIN Log.Char(' '); LogCmdr; Log.String("XoppcSystem." + cmd) END LogSystemCmd; PROCEDURE ObjFrmCmdEnd; BEGIN objFrm.WriteView(DevCommanders.dir.NewEnd()) END ObjFrmCmdEnd; PROCEDURE ObjFrmHex (val: INTEGER); BEGIN objFrm.WriteChar('0'); objFrm.WriteIntForm(val MOD 100000000L, Log.hexadecimal, 1, ' ', Log.hideBase); objFrm.WriteChar('H') END ObjFrmHex; PROCEDURE WriteOpenFold; VAR fold: StdFolds.Fold; text: TextModels.Model; BEGIN text := TextModels.dir.NewFromString(""); fold := StdFolds.dir.New(StdFolds.expanded, "", text); objFrm.WriteView(fold) END WriteOpenFold; PROCEDURE WriteCloseFoldAndFold; VAR fold: StdFolds.Fold; len: INTEGER; BEGIN fold := StdFolds.dir.New(StdFolds.expanded, "", NIL); objFrm.WriteView(fold); fold.Flip; len := objFrm.rider.Base().Length(); objFrm.SetPos(len) END WriteCloseFoldAndFold; PROCEDURE ConnectGlobalScannerToCmdParams; VAR parText: TextModels.Model; BEGIN XU.GetTextModel("@!", parText, gScnrBeg, gScnrEnd); gScnr.ConnectTo(parText); gScnr.SetOpts({XU.soReturnQualIdents, XU.soReturnViews}); gScnr.SetPos(gScnrBeg) END ConnectGlobalScannerToCmdParams; PROCEDURE ShowTargetState; BEGIN IF BDI.isTargetInDebugMode() THEN Log.String("target in debug mode"); LogSystemCmd("TargetGo ?"); Log.Ln ELSE Log.String("target running"); LogSystemCmd("TargetBreak ?"); Log.Ln END END ShowTargetState; PROCEDURE GetTargetStateAndBreak; BEGIN tmpTargetInDebugMode := BDI.isTargetInDebugMode(); BDIMain.ConnectDevice; IF ~BDI.isTargetInDebugMode() THEN IF ~BDI.isFreezeAsserted () THEN BDI.break_ END END END GetTargetStateAndBreak; PROCEDURE TurnTargetToPrevState; BEGIN IF BDI.isTargetInDebugMode () & ~tmpTargetInDebugMode THEN BDI.go END END TurnTargetToPrevState; PROCEDURE TKernelConst * (IN name: ARRAY OF CHAR): INTEGER; (** Returns the value of any global constant of module TobKernel. name is the const name without the module name. Note: open the file with ToppcKernelRefOpen and than fetch constants in alphabetic order to speed up. Exmpl: ramSize := ToppcKernelConst("CintRamSize"); *) VAR cv: ConstVarDesc; BEGIN OBJ.SelectGlobalModuleItem(kernelModName, name, CC.omConst, cv); (* PrintCV(cv); Log.Ln; *) IF cv.objMode = 0 THEN Error(13) ELSE kernItemName := cv.name$ END; RETURN cv.valueAdr END TKernelConst; PROCEDURE TKernelVarOffset (name: ARRAY OF CHAR): INTEGER; VAR val: INTEGER; c0, c1: CHAR; cv: ConstVarDesc; BEGIN OBJ.SelectGlobalModuleItem(kernelModName, name, CC.omVar, cv); (* PrintCV(cv); Log.Ln; *) IF cv.objMode = 0 THEN HALT(19); Error(14) ELSE kernItemName := cv.name$ END; RETURN cv.valueAdr END TKernelVarOffset; PROCEDURE ShowSystemTable * ; (** Shows the content of the system table in System.Log *) BEGIN TMM.ShowSystemTable; END ShowSystemTable; PROCEDURE InsertVar (name: ARRAY OF CHAR; pos: INTEGER); VAR n: INTEGER; BEGIN IF nofVars < LEN(variables) THEN n := nofVars - 1; WHILE (n >= 0) & (name < variables[n].lname) DO variables[n + 1] := variables[n]; DEC(n) END; INC(n); variables[n].lname := name$; variables[n].textPos := pos; variables[n].valueAdr := 0; variables[n].ind := 0; variables[n].form := 0; variables[n].size := 0; variables[n].baseForm := 0; INC(nofVars) END END InsertVar; PROCEDURE PrintVariable (n: SHORTINT); BEGIN Log.Ln; Log.String("Variable["); LogInt(n); Log.String("]: "); Log.String("name="); Log.String(variables[n].name$); Log.String(", textPos "); LogInt(variables[n].textPos); Log.Ln; Log.Tab; Log.String("adr="); LogHex(variables[n].valueAdr); Log.String(", ind="); LogInt(variables[n].ind); Log.String(", form="); LogInt(variables[n].form); Log.String(", size="); LogInt(variables[n].size); Log.String(", baseType="); LogInt(variables[n].baseForm); Log.Ln END PrintVariable; (* PROCEDURE PrintVars; VAR n: SHORTINT; BEGIN n := 0; WHILE n < nofVars DO PrintVariable(n); INC(n) END END PrintVars; *) PROCEDURE WriteRegToLog (regName: ARRAY OF CHAR; VAR done: BOOLEAN); VAR val: LONGINT; hexVal, size: INTEGER; BEGIN Log.String(regName$); Log.String(" = "); RegDict.ReadReg(regName, val, size, done); IF ~done THEN SyntaxErrorAtScnrPos(gScnr.Pos(), 8); RETURN END; IF size <= 4 THEN hexVal := SHORT(val); IF size < 4 THEN IF size > 1 THEN hexVal := hexVal MOD 10000H ELSE hexVal := hexVal MOD 100H END; END; LogHex(hexVal); Log.String("(*" ); LogInt(SHORT(val)); Log.String("*)"); Log.Ln ELSIF size = 8 THEN Log.Real(SYS.VAL(REAL, val)) END END WriteRegToLog; PROCEDURE OutNum (hexVal, decVal, cardinal: INTEGER); BEGIN objFrm.WriteString(" "); ObjFrmHex(hexVal); objFrm.WriteString("(*"); objFrm.WriteInt(decVal); IF cardinal # 0 THEN objFrm.WriteString(" | "); objFrm.WriteInt(cardinal) END; objFrm.WriteString("*)") END OutNum; PROCEDURE OutItem (val: INTEGER; form: INTEGER); VAR card: INTEGER; real: SHORTREAL; int: SHORTINT; short: BYTE; c: CHAR; BEGIN card := 0; CASE form OF |sfBool: val := val MOD 100H; objFrm.WriteString(" "); ObjFrmHex(val); IF val = 0 THEN objFrm.WriteString("(*FALSE*)") ELSE objFrm.WriteString("(*TRUE*)") END; |sfShChar: c := SHORT(CHR(val)); IF (c >= ' ') & (c <= '~') THEN objFrm.WriteChar(c) ELSE objFrm.WriteChar('.') END; |sfByte: short := SHORT(SHORT(val)); IF short < 0 THEN card := LONG(short) + 100H END; OutNum(val MOD 100H, short, card) |sfShInt: int := SHORT(val); IF int < 0 THEN card := LONG(int) + 10000H END; OutNum(val MOD 10000H, int, card) |sfInt: OutNum(val, val, 0) |sfShReal: objFrm.WriteString(" "); real := SYS.VAL(SHORTREAL, val); objFrm.WriteReal(real); objFrm.WriteString("(*"); ObjFrmHex(val); objFrm.WriteString("*)") ELSE objFrm.WriteString(" "); ObjFrmHex(val) END END OutItem; PROCEDURE ReadMemLocs (memAddr: INTEGER; itemSize, len, form, ident: INTEGER); VAR memData, m, i: INTEGER; itemsPerLine: SHORTINT; BEGIN itemsPerLine := 4; IF itemSize = 1 THEN itemsPerLine := 8 END; IF form = sfShChar THEN itemsPerLine := 256 END; m := 0; IF len > 256 THEN len := 256 END; LOOP IF m = 0 THEN memData := BDI.readMem(memAddr, itemSize); OutItem(memData, form); m := itemsPerLine; ELSE memData := BDI.readMemSeq(itemSize); OutItem(memData, form) END; IF ~BDI.Done THEN Error(41); EXIT END; INC(memAddr, LONG(itemSize)); DEC(len); IF len <= 0 THEN EXIT END; DEC(m); IF m = 0 THEN ObjFrmCmdEnd; objFrm.WriteLn; FOR i := 1 TO ident DO objFrm.WriteTab END END END; ObjFrmCmdEnd END ReadMemLocs; PROCEDURE ReadMem (form: INTEGER); VAR c: CHAR; ch: CHAR; memAddr: INTEGER; len, itemSize: INTEGER; BEGIN ConnectGlobalScannerToCmdParams; IF ~gScnr.done THEN Error(22); RETURN END; gScnr.SetOpts({XU.soSkipComments, XU.soScanComments, XU.soReturnViews}); itemSize := formSizes[form]; gScnr.Int(memAddr); IF ~gScnr.done THEN SyntaxErrorAtScnrPos(gScnr.Pos(), 21); RETURN END; gScnr.Char(ch); c := SHORT(ch); IF ~gScnr.done OR (c # ':') THEN SyntaxErrorAtScnrPos(gScnr.Pos() - 1, 05); RETURN END; gScnr.Int(len); IF ~gScnr.done THEN SyntaxErrorAtScnrPos(gScnr.Pos(), 23); RETURN END; GetTargetStateAndBreak; objText := TextModels.dir.New(); IF objText # NIL THEN NEW(objFrm); objFrm.ConnectTo(objText) END; ReadMemLocs(memAddr, itemSize, len, form, 0); objFrm.WriteLn; Log.text.Append(objText); TurnTargetToPrevState; ShowTargetState END ReadMem; PROCEDURE TargetInitSuccessful * (done: BOOLEAN); (** Indicates successful initialisation of the target, called by proc Init in module Target. *) BEGIN Done := done; END TargetInitSuccessful; PROCEDURE ReadVar * ; (** parameters: varName {varName} "żżE". varName = moduleName "." variableName. Shows the content of the variables listed in the parameter list. Var name need to be qualified by the module name. *) VAR mod: TMM.TargetModule; itemSize: INTEGER; len, dotPos, n, timeInt, pos: INTEGER; ident, m: INTEGER; name: LongName; modName, impModName, varName: Name; tempName: ARRAY 32 OF CHAR; refTextModel: TextModels.Model; c0, c1: CHAR; name2: ARRAY 64 OF CHAR; cv: ConstVarDesc; PROCEDURE ^ReadVarPointer (modName: Name; ptr: INTEGER); PROCEDURE GetTdName (ptrTd: INTEGER; OUT name: Name); VAR i, val, nameAdr: INTEGER; BEGIN nameAdr := BDI.readMem(ptrTd + CC.tdoTdNameAddr, 4); (* get adr of td name *) len := BDI.readMem(nameAdr, 4); (* get length of name *) INC(nameAdr, 4); FOR i := 0 TO len - 1 DO val := BDI.readMem(nameAdr + i, 1); name[i] := CHR(SHORT(val)) END; name[i] := 0X; END GetTdName; PROCEDURE GetTypeDesc (IN modName, tdName: Name): INTEGER; VAR glsBase, ptrTd, i: INTEGER; name: Name; BEGIN glsBase := TMM.VarGlsBase( TMM.ThisLoadedModule(modName)); ptrTd := BDI.readMem(glsBase - 4, 4); (* get pointer to first td *) GetTdName(ptrTd, name); i := 1; WHILE name # tdName DO ptrTd := BDI.readMem(glsBase - 4 * i, 4); INC(i); GetTdName(ptrTd, name) END; RETURN ptrTd END GetTypeDesc; PROCEDURE ReadVarComplex (modName: Name; tdNr, extLevel: INTEGER; VAR adr: INTEGER); VAR i, k, m, memData, ptrTd, fieldCount, mno: INTEGER; baseTypePtrOff, baseTdmodNameAdr, baseTypePrtOffset, newExtLevel: INTEGER; tdName, baseTdName, impModName: Name; cv: ConstVarDesc; BEGIN OBJ.Open(modName); OBJ.GetTdName(tdNr, tdName, fieldCount); ptrTd := GetTypeDesc(modName, tdName); IF extLevel = 0 THEN objFrm.WriteChar(' '); IF tdName[0] = "?" THEN objFrm.WriteString("RECORD"); ELSE objFrm.WriteString(tdName) END; IF tdName[1] = "^" THEN objFrm.WriteString(" ("); ObjFrmHex(adr); objFrm.WriteString(")"); END; INC(ident); END; WriteOpenFold; newExtLevel := BDI.readMem(ptrTd + CC.tdoExtLevel, 4); (* get extension level *) IF newExtLevel > 0 THEN (* objFrm.WriteString("go to extension");objFrm.WriteLn; *) baseTypePtrOff := BDI.readMem(ptrTd + CC.tdoBaseTdAddr, 4); (* get base type *) (* GetTdName(baseType, baseTdName);*) (* objFrm.WriteString("base type "); objFrm.WriteString(baseTdName); objFrm.WriteLn;*) mno := BDI.readMem(ptrTd + CC.tdoBaseTdModNr, 4); (* get base type module nr *) IF mno # 0 THEN (* objFrm.WriteString("mno # 0");objFrm.WriteLn; *) OBJ.OpenObj(modName); OBJ.GetImportModName(mno, impModName); ReadVarComplex(impModName, ABS(baseTypePtrOff) DIV 4, newExtLevel, adr) ELSE (* objFrm.WriteString("mno = 0");objFrm.WriteLn; *) ReadVarComplex(modName, ABS(baseTypePtrOff) DIV 4, newExtLevel, adr) END; END; FOR i := 0 TO fieldCount - 1 DO (* objFrm.WriteString("do field "); objFrm.WriteInt(i); objFrm.WriteLn;*) objFrm.WriteLn; OBJ.Open(modName); OBJ.GetTdName(tdNr, tdName, fieldCount); FOR k := 0 TO i DO OBJ.GetTdNextField(cv) END; FOR m := 1 TO ident DO objFrm.WriteTab END; objFrm.WriteString(cv.name); objFrm.WriteChar(':'); IF cv.form = sfComp THEN INC(adr, (- adr) MOD 4); IF cv.baseForm = sfUndef THEN (* record *) IF cv.mno # 0 THEN OBJ.OpenObj(modName); OBJ.GetImportModName(cv.mno, impModName); ReadVarComplex(impModName, cv.td, 0, adr) ELSE ReadVarComplex(modName, cv.td, 0, adr) END ELSIF cv.baseForm = sfComp THEN (* array of record *) WHILE cv.n > 0 DO objFrm.WriteLn; INC(ident); FOR m := 1 TO ident DO objFrm.WriteTab END; ReadVarComplex(modName, cv.td, 0, adr); DEC(cv.n); DEC(ident) END ELSIF cv.baseForm = sfPointer THEN (* array of pointer *) WHILE cv.n > 0 DO objFrm.WriteLn; INC(ident); FOR m := 1 TO ident DO objFrm.WriteTab END; IF cv.mno # 0 THEN OBJ.OpenObj(modName); OBJ.GetImportModName(cv.mno, impModName); ReadVarPointer(impModName, adr) ELSE ReadVarPointer(modName, adr) END; INC(adr, 4); DEC(cv.n); DEC(ident) END ELSE (* array of base type *) objFrm.WriteLn; INC(ident); FOR m := 1 TO ident DO objFrm.WriteTab END; itemSize := formSizes[cv.baseForm]; len := cv.size DIV itemSize; INC(adr, (- adr) MOD itemSize); ReadMemLocs(adr, itemSize, len, cv.baseForm, ident); INC(adr, cv.size); DEC(ident); END ELSIF cv.form = sfPointer THEN INC(adr, (- adr) MOD 4); ReadVarPointer(modName, adr); INC(adr, formSizes[sfPointer]) ELSE (* base type *) itemSize := formSizes[cv.form]; len := cv.size DIV itemSize; INC(adr, (- adr) MOD cv.size); ReadMemLocs(adr, itemSize, len, cv.form, ident); INC(adr, cv.size) END; END; INC(adr, (- adr) MOD 4); IF extLevel = 0 THEN DEC(ident) END; WriteCloseFoldAndFold; END ReadVarComplex; PROCEDURE ReadVarPointer (modName: Name; ptr: INTEGER); VAR tdName: Name; adr, tag, tdNr: INTEGER; BEGIN objFrm.WriteTab; objFrm.WriteString("POINTER TO "); adr := BDI.readMem(ptr, 4); IF adr = 0 THEN objFrm.WriteString("NIL") ELSE tag := BDI.readMem(adr - 4, 4); (* get tag *) GetTdName(tag, tdName); OBJ.Open(modName); OBJ.SearchTdName(modName, tdName, tdNr); ReadVarComplex(modName, tdNr, 0, adr); END END ReadVarPointer; BEGIN Done := TRUE; nofVars := 0; c1 := nul; ConnectGlobalScannerToCmdParams; IF ~gScnr.done THEN Error(22); RETURN END; gScnr.SetOpts({XU.soReturnQualIdents, XU.soReturnViews, XU.soSkipComments, XU.soScanComments}); IF gScnr.Next() = XU.stInt THEN gScnr.Int(timeInt) END; pos := gScnr.Pos(); gScnr.Ident(name2); name := SHORT(name2$); WHILE gScnr.done & (nofVars < LEN(variables)) DO InsertVar(name, pos); pos := gScnr.Pos(); gScnr.Ident(name2); name := SHORT(name2$); END; IF nofVars = 0 THEN SyntaxErrorAtScnrPos(pos, 11); RETURN END; IF gScnr.done THEN Error(19) END; GetTargetStateAndBreak; n := 0; objText := TextModels.dir.New(); IF objText # NIL THEN NEW(objFrm); objFrm.ConnectTo(objText) END; LOOP name := variables[n].lname; pos := variables[n].textPos; len := LEN(name$); Strings.Find(name$, ".", 0, dotPos); IF (len = 0) OR (dotPos <= 0) THEN SyntaxErrorAtScnrPos(pos, 24); EXIT END; Strings.Extract(name$, 0, dotPos, modName); mod := TMM.ThisLoadedModule(modName); IF mod = NIL THEN SyntaxErrorAtScnrPos(pos, 25); EXIT END; Strings.Extract(name$, dotPos + 1, len - dotPos - 1, varName); OBJ.SelectGlobalModuleItem(modName, varName, CC.omVar, cv); IF cv.objMode = CC.omUndef THEN SyntaxErrorAtScnrPos(pos, 14); EXIT END; variables[n].lname := name$; variables[n].ind := CC.omVar; variables[n].valueAdr := cv.valueAdr + TMM.VarGlsBase(mod); variables[n].form := cv.form; variables[n].size := cv.size; variables[n].baseForm := cv.baseForm; variables[n].td := cv.td; variables[n].mno := cv.mno; variables[n].n := cv.n; objFrm.WriteString("Var: "); objFrm.WriteString(variables[n].lname$); objFrm.WriteLn; objFrm.WriteTab; ObjFrmHex(variables[n].valueAdr); objFrm.WriteChar(':'); ident := 1; IF variables[n].form = sfComp THEN IF variables[n].baseForm = sfUndef THEN (* record *) IF variables[n].mno # 0 THEN OBJ.OpenObj(modName); OBJ.GetImportModName(variables[n].mno, impModName); ReadVarComplex(impModName, variables[n].td, 0, variables[n].valueAdr) ELSE ReadVarComplex(modName, variables[n].td, 0, variables[n].valueAdr) END ELSIF variables[n].baseForm = sfComp THEN (* array of record *) WHILE variables[n].n > 0 DO objFrm.WriteLn; INC(ident); FOR m := 1 TO ident DO objFrm.WriteTab END; ReadVarComplex(modName, variables[n].td, 0, variables[n].valueAdr); DEC(variables[n].n); DEC(ident) END ELSIF variables[n].baseForm = sfPointer THEN (* array of pointer *) WHILE variables[n].n > 0 DO objFrm.WriteLn; FOR m := 1 TO ident DO objFrm.WriteTab END; IF variables[n].mno # 0 THEN OBJ.OpenObj(modName); OBJ.GetImportModName(variables[n].mno, impModName); ReadVarPointer(impModName, variables[n].valueAdr) ELSE ReadVarPointer(modName, variables[n].valueAdr) END; INC(variables[n].valueAdr, 4); DEC(variables[n].n); END ELSE (* array of base type *) objFrm.WriteLn; INC(ident); FOR m := 1 TO ident DO objFrm.WriteTab END; itemSize := formSizes[variables[n].baseForm]; len := variables[n].size DIV itemSize; ReadMemLocs(variables[n].valueAdr, itemSize, len, variables[n].baseForm, ident); END ELSIF variables[n].form = sfPointer THEN (* pointer *) IF variables[n].mno # 0 THEN OBJ.OpenObj(modName); OBJ.GetImportModName(variables[n].mno, impModName); ReadVarPointer(impModName, variables[n].valueAdr) ELSE ReadVarPointer(modName, variables[n].valueAdr) END; ELSE (* base type *) IF dbgDetails THEN DlStringLn("base type") END; itemSize := formSizes[ variables[n].form]; len := variables[n].size DIV itemSize; ReadMemLocs(variables[n].valueAdr, itemSize, len, variables[n].form, 0); END; objFrm.WriteLn; INC(n); IF n >= nofVars THEN EXIT END; (* gScnr.Ident(name2); name := SHORT(name2$);*) END; Log.text.Append(objText); TurnTargetToPrevState; ShowTargetState; END ReadVar; PROCEDURE WriteMem (form: SHORTINT); VAR c: CHAR; memAddr, memStartAddr, memData: INTEGER; n, itemSize: SHORTINT; BEGIN BDIMain.ConnectDevice; n := 0; itemSize := formSizes[form]; ConnectGlobalScannerToCmdParams; IF ~gScnr.done THEN Error(22); RETURN END; gScnr.SetOpts({XU.soSkipComments, XU.soScanComments, XU.soReturnViews}); gScnr.Int(memStartAddr); IF ~gScnr.done THEN SyntaxErrorAtScnrPos(gScnr.Pos(), 21); RETURN END; gScnr.Char(c); IF ~gScnr.done OR (c # ':') THEN SyntaxErrorAtScnrPos(gScnr.Pos() - 1, 05); RETURN END; gScnr.Int(memData); IF ~gScnr.done THEN SyntaxErrorAtScnrPos(gScnr.Pos(), 26); RETURN END; Log.Ln; Log.String("writing to memory:"); Log.Ln; LogHex(memStartAddr); Log.Char(':'); Log.Ln; GetTargetStateAndBreak; BDI.writeMem(memStartAddr, memData, itemSize); OutItem(memData, form); memAddr := memStartAddr; LOOP IF ~BDI.Done THEN EXIT END; INC(n, itemSize); INC(memAddr, itemSize); IF gScnr.Next() = XU.stChar THEN gScnr.Char(c); IF c = '~' THEN Log.String("~"); Log.Ln; gScnr.Int(memAddr); IF ~gScnr.done THEN EXIT END; gScnr.Char(c); IF ~gScnr.done OR (c # ':') THEN EXIT END; LogHex(memAddr); Log.Char(':'); END; END; gScnr.Int(memData); IF gScnr.done THEN BDI.writeMem(memAddr, memData, itemSize); OutItem(memData, form); ELSE EXIT END; END; Log.Ln; LogInt(n); Log.String(" bytes written to memory"); Log.Tab; LogSystemCmd("ReadMem"); Log.String(itemNames[itemSize]$); Log.Char(' '); LogHex(memStartAddr); Log.String(": "); LogInt(n DIV itemSize); LogCmdrEnd; Log.Ln; TurnTargetToPrevState; ShowTargetState END WriteMem; PROCEDURE WriteReg * (regName: ARRAY OF CHAR; val: INTEGER; VAR stillOk: BOOLEAN); (* Sets the register defined by regName to val. regName must be member of the register dictionary (module RegDict). stillOk := stillOk & operation successful *) VAR found: BOOLEAN; BEGIN RegDict.WriteReg(regName, val, found); stillOk := stillOk & found; END WriteReg; PROCEDURE DumpRegDictionary * ; (** Shows the content of the register dictionary (all registers with there attributes) in System.Log. *) BEGIN Log.Ln; Log.String("register dictionary"); Log.Ln; RegDict.LogRegs; Log.Ln END DumpRegDictionary; (* PROCEDURE ClearUserRegs*; (** Clears the user registers of the target processor (loads them with 0). *) VAR n: INTEGER; BEGIN RegDict.SelectFirstReg(); (*edppc FOR n := 0 TO RegDict.nofRegs-1 DO IF RegDict.RegType() = RegDict.regTypeGPR THEN BDI.WriteUserReg(RegDict.RegCode(), 0) END; RegDict.SelectNextReg() END *) END ClearUserRegs; *) PROCEDURE ReadRegister * ; (** parameters: regName {regName} "żżE". Shows the contents of the registers, listed in the parameter list. *) VAR regName: Name; regReadOk: BOOLEAN; BEGIN Done := TRUE; ConnectGlobalScannerToCmdParams; IF ~gScnr.done THEN Error(22); RETURN END; Log.Ln; LogSystemCmd("WriteRegister"); Log.Ln; gScnr.Ident(regName); IF ~gScnr.done THEN SyntaxErrorAtScnrPos(gScnr.Pos(), 00); RETURN END; GetTargetStateAndBreak; REPEAT WriteRegToLog(regName, regReadOk); gScnr.Ident(regName) UNTIL ~gScnr.done OR ~regReadOk; TurnTargetToPrevState; LogCmdrEnd; Log.Ln; ShowTargetState END ReadRegister; PROCEDURE WriteRegister * ; (** parameters: regAssignment {regAssignment} "żżE". regAssignment = regName "=" value. Loads the listed registers with the given values. *) VAR regName: Name; c: CHAR; val, textPos: INTEGER; validName, regWrOk: BOOLEAN; BEGIN Done := TRUE; ConnectGlobalScannerToCmdParams; IF ~gScnr.done THEN Error(22); RETURN END; gScnr.SetOpts({XU.soSkipComments, XU.soScanComments, XU.soReturnViews}); Log.Ln; Log.String("writing to register(s): "); LogSystemCmd("ReadRegister"); Log.Ln; LOOP gScnr.Ident(regName); textPos := gScnr.start; Log.String(regName); Log.Tab; RegDict.SelectReg(regName, validName); IF ~gScnr.done OR ~validName THEN SyntaxErrorAtScnrPos(gScnr.start, 00); EXIT END; gScnr.Char(c); IF ~gScnr.done OR (c # '=') THEN SyntaxErrorAtScnrPos(gScnr.start, 4); EXIT END; gScnr.Int(val); IF ~gScnr.done THEN SyntaxErrorAtScnrPos(gScnr.start, 26); EXIT END; GetTargetStateAndBreak; RegDict.WriteReg(regName, val, regWrOk); IF ~BDI.Done THEN Error(27); EXIT END; IF gScnr.Next() # XU.stIdent THEN EXIT END END; TurnTargetToPrevState; LogCmdrEnd; Log.Ln; ShowTargetState END WriteRegister; PROCEDURE ReadMemByte * ; (** parameters: address ":" n. Read n bytes at address and show them in System.Log (n <= 256). *) BEGIN ReadMem(sfByte) END ReadMemByte; PROCEDURE ReadMemShort * ; (** parameters: address ":" n. Read n shortInts (2 byte locations) at address and show them in System.Log (n <= 256). Note: address must be dividable by 2, otherwise it is truncated. *) BEGIN ReadMem(sfShInt) END ReadMemShort; PROCEDURE ReadMemInt * ; (** parameters: address ":" n. Read n integer units (4 byte locations) at address and show them in System.Log (n <= 256). Note: address must be dividable by 4, otherwise it is truncated. *) BEGIN ReadMem(sfInt) END ReadMemInt; PROCEDURE WriteMemByte * ; (** parameters: address ":" value {value} "żżE". Write the list of values to memory, starting at address. The size of each memory location is 1 byte. *) BEGIN WriteMem(sfByte) END WriteMemByte; PROCEDURE WriteMemShort * ; (** parameters: address ":" value {value} "żżE". Write the list of values to memory, starting at address. The size of each memory location is 2 bytes. Note: address must be dividable by 2, otherwise it is truncated. *) BEGIN WriteMem(sfShInt) END WriteMemShort; PROCEDURE WriteMemInt * ; (** parameters: address ":" value {value} "żżE". Write the list of values to memory, starting at address. The size of each memory location is 4 bytes. Note: address must be dividable by 4, otherwise it is truncated. *) BEGIN WriteMem(sfInt) END WriteMemInt; PROCEDURE ResetTarget * ; (** Resets the target board. *) VAR mod: TMM.TargetModule; n, pos, addr: INTEGER; varName: Name; cv: ConstVarDesc; BEGIN BDIMain.ConnectDevice; firstErr := 0; n := 0; mod := TMM.ThisLoadedModule(kernelModName); IF mod = NIL THEN SyntaxErrorAtScnrPos(pos, 25) END; varName := "fprMove"; OBJ.SelectGlobalModuleItem(kernelModName, varName, CC.omVar, cv); IF cv.objMode = CC.omUndef THEN SyntaxErrorAtScnrPos(pos, 14) END; addr := cv.valueAdr + TMM.VarGlsBase(mod); RegDict.fprMoveAddr := addr; BDI.reset_target; IF BDI.Done THEN BDI.writeMem(02FC000H, 40000H, 4); (* assign pin to Freeze output *) BDI.writeMem(02FC004H, 0FFFFFF83H, 4); (* enable bus monitor, disable watchdog timer *) BDI.writeMem(02FC280H, 08121C100H, 4) (* SCCR, switch off EECLK for download *) END; IF BDI.Done THEN Log.String("ResetTarget done"); Log.Ln ELSE Log.String("ResetTarget failed"); Log.Ln; END; END ResetTarget; PROCEDURE ResetHost * ; (** Resets the cross system. *) VAR n: SHORTINT; BEGIN Done := TRUE; firstErr := 0; IF (Dialog.platform >= Dialog.windows32s) & (Dialog.platform <= Dialog.windows98) THEN Fcs := NIL ELSE Error(51) END; TMM.Clear; LogLine("cross system reset"); itemNames[0] := "*****"; itemNames[3] := "*****"; itemNames[1] := "Byte"; itemNames[2] := "Word"; itemNames[4] := "Long"; (*OPT Structure Forms (standard types) *) FOR n := 0 TO LEN(formSizes) - 1 DO formSizes[n] := 4 END; formSizes[sfUndef] := 1; formSizes[sfSysByte] := 1; formSizes[sfBool] := 1; formSizes[sfShChar] := 1; formSizes[sfByte] := 1; formSizes[sfShInt] := 2; formSizes[sfReal] := 8; formSizes[sfString] := 1; (* SystemConstantsSetUp *) END ResetHost; PROCEDURE Build * ; (** parameters: moduleName ["/" memDeviceName] {moduleName ["/" memDeviceName]} "żżE". description: Resets the target board, selects the modules given by the parameter list and all other modules according to their import lists. It then evaluates the size of code and variables, activates Target.DefineMemory and generates for each memory component an memory image file. The memory component RAM is the default component. All code which can be loaded into the target ram is put to file "RAM.Tim". The command XoppcSystem.LoadRam loads this image to the target ram and brings the target into the state ready to go. *) VAR mod: TMM.TargetModule; name: Name; targAdr, nofErrorsAtBegin: INTEGER; m, n, memDeviceId: INTEGER; codeInRam, codeInReadOnly: BOOLEAN; BEGIN Done := TRUE; nofErrors := 0; nofErrorsAtBegin := Errors.nofErrors; configT := TextModels.dir.New(); configTextForm.ConnectTo(configT); XU.Register(configT, NIL, "Tim/" + configText); Log.Ln; Log.String("XoppcSystem: building starts"); Log.Ln; TMM.Build; TMM.WriteImageFiles; Done := TMM.Done; Log.Ln; Log.Tab; Log.String("system build completed with"); Log.Tab; nofErrors := SHORT(Errors.nofErrors - nofErrorsAtBegin); LogInt(nofErrors); Log.String(" errors"); Log.Ln; Log.Ln END Build; PROCEDURE LoadRam * ; (** Preconditions: the targets Read Only Memory Deviceonents are up to date (click on XoppcSystem.CheckReadOnlyMem) there is an image file RAM.Tim if neccessary, click on XoppcSystem.Build to update all images Description: the image in file RAM.Tim is loaded to the target ram. Postconditions: the target is ready to go: click on: XoppcSystem.TargetGo *) CONST logOn = FALSE; VAR header: IMF.Header; addr, len, offset, size, intVal, fixedHdrAddr: INTEGER; res, n, downloadLength, i: INTEGER; codeBlock: ARRAY 256 OF INTEGER; name: Name; data: ARRAY MAX_NOF_WORDS_FAST_DOWNLOAD OF INTEGER; firstAddrSet: BOOLEAN; index: INTEGER; BEGIN Done := TRUE; ResetTarget; (* FIXME GetTargetStateAndBreak; *) IF ~BDI.Done THEN Error(40); RETURN END; Log.Tab; Log.String("controller reset and initialised"); Log.Ln; Log.Ln; Log.String("loading of target RAM from file "); TMM.InitRegs; header.devName := "RAM"; Log.String(header.devName); Log.String(" starts"); Log.Ln; IMF.OpenRead(header); Log.String("Download:"); Log.Ln; IF COMPARE_IMAGE THEN firstAddrSet := FALSE; index := 0; FOR i := 0 TO LEN(addrList) - 1 DO addrList[i] := 0; END END; REPEAT IMF.ReadDataBlock(addr, len, codeBlock); IF COMPARE_IMAGE THEN IF ~firstAddrSet THEN firstAddrSet := TRUE; END; FOR i := 0 TO len - 1 DO addrList[index + i] := addr + i * 4; dataList[index + i] := codeBlock[i] END; END; IF dbgDetails THEN DlHex(addr); DlTab; DlInt(len); DlTab; DlHex(codeBlock[0]); DlTab; DlHex(codeBlock[1]); DlLn END; IF len > 0 THEN BDI.startFastDownload(addr); IF logOn THEN Log.String("startFastDownload: addr = "); LogHex(addr); Log.Ln; END; n := 0; WHILE (n < len) & BDI.Done DO downloadLength := MAX_NOF_WORDS_FAST_DOWNLOAD; IF len - n < MAX_NOF_WORDS_FAST_DOWNLOAD THEN downloadLength := len - n; END; FOR i := 0 TO downloadLength - 1 DO data[i] := codeBlock[n + i]; IF logOn THEN Log.String("addr: "); LogHex(addr + (n + i) * 4); Log.String(", i: "); Log.Int(i); Log.String(", n + i: "); Log.Int(n + i); Log.String(", val: "); LogHex(data[i]); Log.Ln; END END; INC(n, downloadLength); BDI.fastDownload(data, downloadLength); IF logOn THEN Log.String("downloadLength "); Log.Int(downloadLength); Log.Ln; END END; BDI.stopFastDownload; END; Log.Char('.'); index := index + len; UNTIL IMF.eof OR ~IMF.Done OR ~BDI.Done; maxDataListIndex := index; Log.Ln; ASSERT(IMF.Done, 99); IMF.Close; sysTabBase := TKernelConst("sysTabAdr"); offset := TKernelConst("stoSysTabSize") DIV 4; codeBlock[0] := BDI.readMem(sysTabBase, 4); n := 1; REPEAT codeBlock[n] := BDI.readMemSeq(4); INC(n) UNTIL (n > offset) OR ~BDI.Done; sysTabSize := codeBlock[offset]; NEW(sysTab, sysTabSize DIV 4); sysTab[0] := BDI.readMem(sysTabBase, 4); n := 1; REPEAT sysTab[n] := BDI.readMemSeq(4); INC(n) UNTIL (n >= LEN(sysTab^)) OR ~BDI.Done; IF ~Done THEN Error(41) END; offset := TKernelConst("stoStacksOffset") DIV 4; offset := sysTab[offset] DIV 4; addr := sysTab[offset + 1]; size := sysTab[offset + 2]; BDI.setGpr31(addr + size); (* will be moved into R31 when leaving debug mode *) offset := TKernelConst("stackOffset"); WriteReg("R1", addr + size + offset, Done); offset := TKernelConst("stoModulesOffset") DIV 4; offset := sysTab[offset] DIV 4; addr := sysTab[offset + 2]; offset := BDI.readMem(addr, 4); (* nofPointers of ToppcKernel *) fixedHdrAddr := addr + 4 + offset * 4; offset := TKernelConst("cbfhoGlobVarBlkBase"); (* get globVarBlkBase*) intVal := BDI.readMem(fixedHdrAddr + offset, 4); WriteReg("R2", intVal, Done); (* set R2 to varGlsBase of ToppcKernel *) VcommandAdr := TKernelVarOffset("Vcommand") + intVal; offset := TKernelConst("cbfhoBodyAddr"); intVal := BDI.readMem(fixedHdrAddr + offset, 4); WriteReg("SRR0", intVal, Done); (* set to bodyAddr of ToppcKernel *) (* WriteReg("SRR1", 02802H, Done); (* set MSR *) is done in MemMap File*) IF ~Done THEN Error(42) ELSE Log.Ln; Log.String("XoppcSystem: ram image successfully loaded"); Log.Ln; ShowTargetState END END LoadRam; PROCEDURE LoadRamDebug * ; (** Preconditions: the targets Read Only Memory Deviceonents are up to date (click on XoppcSystem.CheckReadOnlyMem) there is an image file RAM.Tim if neccessary, click on XoppcSystem.Build to update all images Description: the image in file RAM.Tim is loaded to the target ram. Postconditions: the target is ready to go: click on: XoppcSystem.TargetGo *) CONST logOn = TRUE; compareDirect = TRUE; compareDirectLogOn = FALSE; VAR header: IMF.Header; addr, len, offset, size, intVal, fixedHdrAddr: INTEGER; res, n, downloadLength, i: INTEGER; codeBlock: ARRAY 256 OF INTEGER; name: Name; data: ARRAY MAX_NOF_WORDS_FAST_DOWNLOAD OF INTEGER; firstAddrSet: BOOLEAN; index: INTEGER; BEGIN Done := TRUE; ResetTarget; IF ~BDI.Done THEN Error(40); RETURN END; Log.Tab; Log.String("controller reset and initialised"); Log.Ln; Log.Ln; Log.String("loading of target RAM from file "); TMM.InitRegs; header.devName := "RAM"; Log.String(header.devName); Log.String(" starts"); Log.Ln; IMF.OpenRead(header); Log.String("Download:"); Log.Ln; IF COMPARE_IMAGE THEN firstAddrSet := FALSE; index := 0; FOR i := 0 TO LEN(addrList) - 1 DO addrList[i] := 0; END END; REPEAT IMF.ReadDataBlock(addr, len, codeBlock); IF COMPARE_IMAGE THEN IF ~firstAddrSet THEN firstAddrSet := TRUE; END; FOR i := 0 TO len - 1 DO addrList[index + i] := addr + i * 4; dataList[index + i] := codeBlock[i] END; END; IF dbgDetails THEN DlHex(addr); DlTab; DlInt(len); DlTab; DlHex(codeBlock[0]); DlTab; DlHex(codeBlock[1]); DlLn END; IF len > 0 THEN (* BDI.startFastDownload(addr); *) n := 0; WHILE (n < len) & BDI.Done DO downloadLength := MAX_NOF_WORDS_FAST_DOWNLOAD; IF len - n < MAX_NOF_WORDS_FAST_DOWNLOAD THEN downloadLength := len - n; END; FOR i := 0 TO downloadLength - 1 DO data[i] := codeBlock[n + i]; IF logOn THEN Log.String("addr: "); LogHex(addr + (n + i) * 4); Log.String(", i: "); Log.Int(i); Log.String(", n + i: "); Log.Int(n + i); Log.String(", val: "); LogHex(data[i]); Log.Ln; END END; (* BDI.fastDownload(data, downloadLength); *) FOR i := 0 TO downloadLength - 1 DO BDI.writeMem(addr + (n + i) * 4, data[i], 4); IF compareDirect THEN intVal := BDI.readMem(addr + (n + i) * 4, 4); IF codeBlock[n + i] # intVal THEN Log.String("ERROR at "); LogHex(addr); Log.String(", expected: "); LogHex(codeBlock[n]); Log.String(", read: "); LogHex(intVal); Log.Ln; END; IF compareDirectLogOn THEN Log.String("addr: "); LogHex(addr + (n + i) * 4); Log.String(", val: "); LogHex(codeBlock[n + i]); Log.String(", read: "); LogHex(intVal); Log.Ln; END END END; IF logOn THEN Log.String("downloadLength "); Log.Int(downloadLength); Log.Ln; END; INC(n, downloadLength); END; (* BDI.stopFastDownload; *) END; (* WHILE (n < len) & BDI.Done DO BDI.writeMem(addr + n*4, codeBlock[n], 4); IF compareDirect THEN intVal := BDI.readMem(addr + n*4, 4); IF codeBlock[n] # intVal THEN Log.String("ERROR at "); LogHex(addr); Log.String(", expected: "); LogHex(codeBlock[n]); Log.String(", read: "); LogHex(intVal); Log.Ln; END; IF logOn THEN Log.String("addr: "); LogHex(addr + n*4); Log.String(", val: "); LogHex(codeBlock[n]); Log.String(", read: "); LogHex(intVal); Log.Ln; END; (* IF addr > 0802000H THEN intVal := BDI.readMem(0802000H, 4); Log.String("at 0802000H: "); LogHex(intVal); Log.Ln; intVal := BDI.readMem(0802000H, 4); Log.String("at 0802000H: "); LogHex(intVal); Log.Ln; HALT(35) END *) END; INC(n); END; END; *) Log.Char('.'); index := index + len; UNTIL IMF.eof OR ~IMF.Done OR ~BDI.Done; maxDataListIndex := index; Log.Ln; ASSERT(IMF.Done, 99); IMF.Close; sysTabBase := TKernelConst("sysTabAdr"); offset := TKernelConst("stoSysTabSize") DIV 4; codeBlock[0] := BDI.readMem(sysTabBase, 4); n := 1; REPEAT codeBlock[n] := BDI.readMemSeq(4); INC(n) UNTIL (n > offset) OR ~BDI.Done; sysTabSize := codeBlock[offset]; NEW(sysTab, sysTabSize DIV 4); sysTab[0] := BDI.readMem(sysTabBase, 4); n := 1; REPEAT sysTab[n] := BDI.readMemSeq(4); INC(n) UNTIL (n >= LEN(sysTab^)) OR ~BDI.Done; IF ~Done THEN Error(41) END; offset := TKernelConst("stoStacksOffset") DIV 4; offset := sysTab[offset] DIV 4; addr := sysTab[offset + 1]; size := sysTab[offset + 2]; BDI.setGpr31(addr + size); (* will be moved into R31 when leaving debug mode *) offset := TKernelConst("stackOffset"); WriteReg("R1", addr + size + offset, Done); offset := TKernelConst("stoModulesOffset") DIV 4; offset := sysTab[offset] DIV 4; addr := sysTab[offset + 2]; offset := BDI.readMem(addr, 4); (* nofPointers of ToppcKernel *) fixedHdrAddr := addr + 4 + offset * 4; offset := TKernelConst("cbfhoGlobVarBlkBase"); (* get globVarBlkBase*) intVal := BDI.readMem(fixedHdrAddr + offset, 4); WriteReg("R2", intVal, Done); (* set R2 to varGlsBase of ToppcKernel *) VcommandAdr := TKernelVarOffset("Vcommand") + intVal; offset := TKernelConst("cbfhoBodyAddr"); intVal := BDI.readMem(fixedHdrAddr + offset, 4); WriteReg("SRR0", intVal, Done); (* set to bodyAddr of ToppcKernel *) (* WriteReg("SRR1", 02802H, Done); (* set MSR *) is done in MemMap File*) IF ~Done THEN Error(42) ELSE Log.Ln; Log.String("XoppcSystem: ram image successfully loaded"); Log.Ln; ShowTargetState END END LoadRamDebug; PROCEDURE LoadRamNew * ; (** Preconditions: the targets Read Only Memory Deviceonents are up to date (click on XoppcSystem.CheckReadOnlyMem) there is an image file RAM.Tim if neccessary, click on XoppcSystem.Build to update all images Description: the image in file RAM.Tim is loaded to the target ram. Postconditions: the target is ready to go: click on: XoppcSystem.TargetGo *) CONST logOn = TRUE; compareDirect = TRUE; compareDirectLogOn = FALSE; VAR header: IMF.Header; addr, len, offset, size, intVal, fixedHdrAddr: INTEGER; n, downloadLength, i, codeBlockIndex: INTEGER; codeBlock: ARRAY 256 OF INTEGER; name: Name; downloadData: ARRAY MAX_NOF_WORDS_FAST_DOWNLOAD OF INTEGER; index: INTEGER; PROCEDURE Min (val1, val2: INTEGER): INTEGER; BEGIN IF val1 > val2 THEN RETURN val2 ELSE RETURN val1 END END Min; BEGIN Done := TRUE; ResetTarget; IF ~BDI.Done THEN Error(40); RETURN END; Log.Tab; Log.String("controller reset and initialised"); Log.Ln; Log.Ln; Log.String("loading of target RAM from file "); TMM.InitRegs; header.devName := "RAM"; Log.String(header.devName); Log.String(" starts"); Log.Ln; IMF.OpenRead(header); Log.String("Download:"); Log.Ln; IF COMPARE_IMAGE THEN index := 0; FOR i := 0 TO LEN(addrList) - 1 DO addrList[i] := 0; END END; REPEAT IMF.ReadDataBlock(addr, len, codeBlock); IF COMPARE_IMAGE THEN FOR i := 0 TO len - 1 DO addrList[index + i] := addr + i * 4; dataList[index + i] := codeBlock[i] END END; IF len > 0 THEN BDI.startFastDownload(addr); Log.String("baseAddr = 0x"); Log.IntForm(addr, Log.hexadecimal, 1, ' ', Log.hideBase); Log.String(";"); Log.Ln; Log.String("MPC555.startFastDownload(baseAddr);"); Log.Ln; codeBlockIndex := 0; WHILE (codeBlockIndex < len) & BDI.Done DO downloadLength := Min(MAX_NOF_WORDS_FAST_DOWNLOAD, len - codeBlockIndex); Log.String("length = "); Log.Int(downloadLength); Log.String(";"); Log.Ln; FOR i := 0 TO downloadLength - 1 DO downloadData[i] := codeBlock[codeBlockIndex + i]; Log.String("data["); Log.Int(i); Log.String("] = 0x"); Log.IntForm(codeBlock[codeBlockIndex + i], Log.hexadecimal, 1, ' ', Log.hideBase); Log.String(";"); Log.Ln; END; BDI.fastDownload(downloadData, downloadLength); INC(codeBlockIndex, downloadLength); Log.String("add(baseAddr, data, length);"); Log.Ln; Log.String("MPC555.fastDownload(data, length);"); Log.Ln; END; Log.String("MPC555.stopFastDownload();"); Log.Ln; BDI.stopFastDownload; END; index := index + len; UNTIL IMF.eof OR ~IMF.Done OR ~BDI.Done; maxDataListIndex := index; Log.Ln; ASSERT(IMF.Done, 99); IMF.Close; sysTabBase := TKernelConst("sysTabAdr"); offset := TKernelConst("stoSysTabSize") DIV 4; codeBlock[0] := BDI.readMem(sysTabBase, 4); n := 1; REPEAT codeBlock[n] := BDI.readMemSeq(4); INC(n) UNTIL (n > offset) OR ~BDI.Done; sysTabSize := codeBlock[offset]; NEW(sysTab, sysTabSize DIV 4); sysTab[0] := BDI.readMem(sysTabBase, 4); n := 1; REPEAT sysTab[n] := BDI.readMemSeq(4); INC(n) UNTIL (n >= LEN(sysTab^)) OR ~BDI.Done; IF ~Done THEN Error(41) END; offset := TKernelConst("stoStacksOffset") DIV 4; offset := sysTab[offset] DIV 4; addr := sysTab[offset + 1]; size := sysTab[offset + 2]; BDI.setGpr31(addr + size); (* will be moved into R31 when leaving debug mode *) offset := TKernelConst("stackOffset"); WriteReg("R1", addr + size + offset, Done); offset := TKernelConst("stoModulesOffset") DIV 4; offset := sysTab[offset] DIV 4; addr := sysTab[offset + 2]; offset := BDI.readMem(addr, 4); (* nofPointers of ToppcKernel *) fixedHdrAddr := addr + 4 + offset * 4; offset := TKernelConst("cbfhoGlobVarBlkBase"); (* get globVarBlkBase*) intVal := BDI.readMem(fixedHdrAddr + offset, 4); WriteReg("R2", intVal, Done); (* set R2 to varGlsBase of ToppcKernel *) VcommandAdr := TKernelVarOffset("Vcommand") + intVal; offset := TKernelConst("cbfhoBodyAddr"); intVal := BDI.readMem(fixedHdrAddr + offset, 4); WriteReg("SRR0", intVal, Done); (* set to bodyAddr of ToppcKernel *) (* WriteReg("SRR1", 02802H, Done); (* set MSR *) is done in MemMap File*) IF ~Done THEN Error(42) ELSE Log.Ln; Log.String("XoppcSystem: ram image successfully loaded"); Log.Ln; ShowTargetState END END LoadRamNew; PROCEDURE LoadMem * ; VAR codeBlock: ARRAY 256 OF INTEGER; name: Name; addr, len: INTEGER; res, n, memStartAddr, memData: INTEGER; c: CHAR; itemSize: SHORTINT; data: ARRAY MAX_NOF_WORDS_FAST_DOWNLOAD OF INTEGER; BEGIN (* FIXME ResetTarget; *) IF ~BDI.isFreezeAsserted() THEN BDI.break_ END; IF ~BDI.Done THEN Error(40); RETURN END; Log.Ln; Log.String("loading of target RAM from input starts"); Log.Ln; n := 0; itemSize := 4; ConnectGlobalScannerToCmdParams; IF ~gScnr.done THEN Error(22); RETURN END; gScnr.SetOpts({XU.soSkipComments, XU.soScanComments, XU.soReturnViews}); gScnr.Int(memStartAddr); IF ~gScnr.done THEN SyntaxErrorAtScnrPos(gScnr.Pos(), 21); RETURN END; gScnr.Char(c); IF ~gScnr.done OR (c # ':') THEN SyntaxErrorAtScnrPos(gScnr.Pos() - 1, 05); RETURN END; gScnr.Int(memData); IF ~gScnr.done THEN SyntaxErrorAtScnrPos(gScnr.Pos(), 26); RETURN END; (* FIXME BDI.startFastDownload(memStartAddr); BDI.WriteMemFast(memData); LOOP IF ~BDI.Done THEN EXIT END; INC(n, itemSize); IF gScnr.Next() = XU.stChar THEN gScnr.Char(c); EXIT END; gScnr.Int(memData); IF gScnr.done THEN BDI.WriteMemFast(memData) ELSE EXIT END; END; BDI.stopFastDownload; Log.Ln; IF ~BDI.Done THEN Error(42) ELSE LogInt(n); Log.String(" bytes written to memory"); Log.Tab; LogSystemCmd("ReadMem"); Log.String(itemNames[itemSize]$); Log.Char(' '); LogHex(memStartAddr); Log.String(": "); LogInt(n DIV itemSize); Log.Char("~"); Log.Ln; TurnTargetToPrevState; ShowTargetState END *) END LoadMem; (* PROCEDURE CheckImage*; VAR codeBlock: ARRAY 256 OF INTEGER; name: Name; addr, romBase, long, len: INTEGER; n, nofIMFs: SHORTINT; ch: SHORTCHAR; error, cmpOk: BOOLEAN; BEGIN Done := TRUE; nofIMFs := 0; Log.Ln; romBase := TKernelConst("CromBase"); In.OpenTextFile("TargetConfig.Text"); LOOP IF ~gScnr.done THEN Error(43); EXIT END; REPEAT IF gScnr.Next() = Utilities.stIdent THEN gScnr.Ident(name) ELSE gScnr.Char(ch) END; UNTIL ~gScnr.done OR (name="ImageFile:") OR (name="END."); IF ~gScnr.done THEN SyntaxErrorAtScnrPos(gScnr.Pos(), 44); EXIT ELSIF name="END." THEN EXIT END; gScnr.Ident(name); IF ~gScnr.done THEN SyntaxErrorAtScnrPos(gScnr.Pos(), 45); EXIT END; Log.String("checking image file: "); Log.String(name); Log.Ln; IMF.OpenRead(name); IF ~IMF.Done THEN SyntaxErrorAtScnrPos(gScnr.Pos(), 46); EXIT END; REPEAT IMF.ReadDataBlock(addr, len, codeBlock); IF len > 0 THEN BDI.ReadMem(addr, long, 4) END; n := 0; WHILE (n < len) & BDI.Done & (codeBlock[n]=long) DO INC(n); BDI.DumpMem(long, 4) END; cmpOk := (n = len) & BDI.Done; error := ~IMF.Done OR ~cmpOk; UNTIL ~cmpOk OR IMF.eof OR error; IF (n < len) & (addr = romBase) & (len=LEN(sysTab^)) THEN Log.String("\nsystem table at "); LogHex(addr+n*4, 0); Log.String(" has changed (might be ok)\n") ELSIF error THEN IF ~IMF.Done THEN Error(47) ELSIF ~BDI.Done THEN Error(48) ELSE Error(50); Log.String("\n\tat mem loc: "); LogHex(addr+n*4, 0); Log.String("\n\tval on target: "); LogHex(long, 0); Log.String("\n\tval in file: "); LogHex(codeBlock[n], 0); Log.Ln END; EXIT END; INC(nofIMFs); END; IF Done THEN IF nofIMFs > 0 THEN Log.Ln; LogInt(nofIMFs, 0); Log.String(" image file(s) checked successfully") ELSE Error(49) END ELSE Log.String("checking terminated with errror") END; Log.Ln END CheckImage; *) PROCEDURE TargetGo * ; (** Resumes execution of the target program at RPC *) BEGIN IF BDI.isFreezeAsserted() THEN BDI.go END; ShowTargetState END TargetGo; PROCEDURE TargetBreak * ; (** Breaks execution of the target program and enters background debug mode. Click XdeSystem.TargetGo to carry on. *) BEGIN IF ~BDI.isFreezeAsserted() THEN BDI.break_ END; ShowTargetState END TargetBreak; PROCEDURE TargetCmd * ; (** Activates the command specified by the parameter. Expl: XoppcSystem.TargetCmd TReflect.ChangeDot activates command ChangeDot of module TReflect on target. *) VAR mod: TMM.TargetModule; cmdAdr, gVarBase: TMM.Command; cmd: LONGINT; name: LongName; p: INTEGER; cmdName: ARRAY 64 OF CHAR; name2: ARRAY 32 OF CHAR; BEGIN ConnectGlobalScannerToCmdParams; IF gScnr.done THEN gScnr.Ident(name2); name := SHORT(name2$); IF ~gScnr.done THEN RETURN END; Strings.Find(name$, ".", 0, p); IF p = 0 THEN RETURN END; Log.String("target cmd: "); Log.String(name$); Strings.Extract(name$, p + 1, LEN(name$) - p - 1, cmdName); name[p] := 0X; mod := TMM.ThisLoadedModule(name); cmd := 0; IF mod # NIL THEN cmd := TMM.ThisCommand(mod, SHORT(cmdName$)) END; cmdAdr := SHORT(cmd DIV 100000000L); gVarBase := SHORT(cmd MOD 100000000L); IF cmdAdr # 0 THEN Log.String(" ["); LogHex(cmdAdr); Log.Char(','); LogHex(gVarBase); Log.Char('['); Log.Ln; GetTargetStateAndBreak; BDI.writeMem(VcommandAdr, cmdAdr, 4); BDI.writeMem(VcommandAdr + 4, gVarBase, 4); TargetGo ELSE Log.String(" not found"); Log.Ln; END; Log.Ln; END END TargetCmd; (* Execute after LoadRam to compare the Image and the downloaded data from the mc *) PROCEDURE CompareImage * ; CONST SHOW_ALL = FALSE; DONT_USE_READMEMSEQ = TRUE; VAR startIndex, i, memData, recLength, oldAddr: INTEGER; sameAddress: BOOLEAN; PROCEDURE LogListError (pos, addr, dataList, dataMC: INTEGER); BEGIN Log.String(" at "); Log.Int(pos); Log.String(", addr: "); Log.IntForm(addr, Log.hexadecimal, 8, ' ', FALSE); Log.String(", dataList: "); Log.IntForm(dataList, Log.hexadecimal, 8, ' ', FALSE); Log.String(", MC: "); Log.IntForm(dataMC, Log.hexadecimal, 8, ' ', FALSE); Log.Ln; END LogListError; BEGIN IF ~COMPARE_IMAGE THEN Log.String("set constant COMPARE_IMAGE to TRUE first"); Log.Ln; RETURN; END; Log.String("CompareImage start"); Log.Ln; startIndex := 0; i := 0; WHILE startIndex < maxDataListIndex DO memData := BDI.readMem(addrList[startIndex], 4); IF SHOW_ALL THEN LogListError(startIndex + i, addrList[startIndex], dataList[startIndex], memData); END; IF memData # dataList[startIndex] THEN Log.String("ERROR1: "); LogListError(startIndex + i, addrList[startIndex], dataList[startIndex], memData); END; i := 1; IF ~DONT_USE_READMEMSEQ THEN sameAddress := TRUE; oldAddr := addrList[startIndex + i] - 4; WHILE sameAddress DO memData := BDI.readMemSeq(4); IF SHOW_ALL THEN LogListError(startIndex + i, addrList[startIndex + i], dataList[startIndex + i], memData); END; IF dataList[startIndex + i] # memData THEN Log.String("ERROR2: "); LogListError(startIndex + i, addrList[startIndex + i], dataList[startIndex + i], memData); END; IF addrList[startIndex + i] # (oldAddr + 4) THEN sameAddress := FALSE ELSE oldAddr := addrList[startIndex + i]; INC(i); END END; END; (* BDI.BDI332_dumpMem(LEN(data), data, recLength); (* Log.String("recLength: "); Log.Int(recLength); Log.Ln; *) i := 1; sameAddress := TRUE; oldAddr := addrList[startIndex + i] - 4; WHILE (i <= recLength) & (sameAddress) DO IF dataList[startIndex + i] # data[i - 1] THEN Log.String("ERROR: "); LogListError(startIndex + i, addrList[startIndex + i], dataList[startIndex + i], data[i - 1]); END; (* Log.String("addrList[startIndex + i] "); Log.Int(addrList[startIndex + i]); Log.String(", (oldAddr + 4)"); Log.Int((oldAddr + 4)); Log.Ln; *) IF addrList[startIndex + i] # (oldAddr + 4) THEN sameAddress := FALSE ELSE oldAddr := addrList[startIndex + i]; INC(i); END; END; *) startIndex := startIndex + i; END; Log.String("CompareImage done"); Log.Ln; END CompareImage; PROCEDURE DownloadTestData * ; CONST BASE_ADDR = 3F9BF0H; VAR data: ARRAY 101 OF INTEGER; BEGIN data[0] := 09421FFB0H; data[1] := 0BF810040H; data[2] := 03BE10038H; data[3] := 03BC30000H; data[4] := 03BA40000H; data[5] := 03C600030H; data[6] := 038836102H; data[7] := 038A08000H; data[8] := 0B0A40000H; data[9] := 02C9E0000H; data[10] := 04085004CH; data[11] := 03CC00030H; data[12] := 038E66100H; data[13] := 039000000H; data[14] := 0B1070000H; data[15] := 01F9D2710H; data[16] := 0339CFFFFH; data[17] := 02F1C0000H; data[18] := 04199FFF8H; data[19] := 03D200030H; data[20] := 039496100H; data[21] := 039608000H; data[22] := 0B16A0000H; data[23] := 01F9D2710H; data[24] := 0339CFFFFH; data[25] := 02F9C0000H; data[26] := 0419DFFF8H; data[27] := 033DEFFFFH; data[28] := 04280FFB4H; data[29] := 0383FFFC8H; data[30] := 0BB810040H; data[31] := 038210050H; data[32] := 04E800020H; data[33] := 09421FFB0H; data[34] := 07C0802A6H; data[35] := 09001004CH; data[36] := 0BFC10044H; data[37] := 03BE10038H; data[38] := 090410014H; data[39] := 07FCC42E6H; data[40] := 0387E0000H; data[41] := 042800008H; data[42] := 07FE00008H; data[43] := 0383FFFC8H; data[44] := 0BBC10044H; data[45] := 08001004CH; data[46] := 07C0803A6H; data[47] := 038210050H; data[48] := 04E800020H; data[49] := 09421FFB8H; data[50] := 07C0802A6H; data[51] := 090010044H; data[52] := 0BFA10038H; data[53] := 03BE10038H; data[54] := 090410014H; data[55] := 03BC30000H; data[56] := 03BA40000H; data[57] := 04BFFFFA1H; data[58] := 090620018H; data[59] := 081820018H; data[60] := 03C60000FH; data[61] := 038834240H; data[62] := 07CAC23D7H; data[63] := 040800008H; data[64] := 030A5FFFFH; data[65] := 090BE0000H; data[66] := 080C20018H; data[67] := 038E003E8H; data[68] := 07D063BD7H; data[69] := 040800008H; data[70] := 03108FFFFH; data[71] := 0392003E8H; data[72] := 07D484BD6H; data[73] := 07D4A49D6H; data[74] := 07D4A4011H; data[75] := 040800008H; data[76] := 0314A03E8H; data[77] := 0B15D0000H; data[78] := 0383FFFC8H; data[79] := 0BBA10038H; data[80] := 080010044H; data[81] := 07C0803A6H; data[82] := 038210048H; data[83] := 04E800020H; data[84] := 09421FF98H; data[85] := 0BF21004CH; data[86] := 03BE10038H; data[87] := 03BC30000H; data[88] := 03BA40000H; data[89] := 03B7E0000H; data[90] := 03B800000H; data[91] := 07C9BE800H; data[92] := 040840070H; data[93] := 0A33B0000H; data[94] := 07F9CCB78H; data[95] := 03B40000FH; data[96] := 0578B0001H; data[97] := 04182000CH; data[98] := 06B8C8000H; data[99] := 06D9C0810H; data[100] := 057830801H; BDI.startFastDownload(BASE_ADDR); BDI.fastDownload(data, LEN(data)); BDI.stopFastDownload; END DownloadTestData; BEGIN Log.Ln; Log.String(signOnMsg); Log.Ln; ResetHost; END XoppcSystem.