DIRECTORY IO USING[STREAM], ObjectFiles USING[BracketPairKind, CGrammar, FileSegmentPC, GlobalVarLoc, Stab, VarLoc, VersionStampInfo], PFSNames USING [PATH], Rope USING[ROPE], SystemInterface USING[CirioFile]; ObjectFilesPrivate: CEDAR DEFINITIONS = BEGIN ROPE: TYPE ~ Rope.ROPE; Stab: TYPE = ObjectFiles.Stab; StabList: TYPE ~ LIST OF Stab; VersionStampInfo: TYPE = ObjectFiles.VersionStampInfo; Parsed: TYPE = REF ParsedBody; ParsedBody: TYPE = RECORD[ file: SystemInterface.CirioFile, targetData: REF ANY, formatSpecificString: ROPE, cGrammar: ObjectFiles.CGrammar, header: Header, privateInfo: REF ANY _ NIL, -- needed for SGI stabLimit: CARD, modules: LIST OF Module]; Module: TYPE = REF ModuleBody; ModuleBody: TYPE = RECORD[ whole: Parsed, moduleWhole: Parsed _ NIL, -- for SunOS5.x fileName: PFSNames.PATH, instance: INT _ 0, firstPC: CARD _ 0, -- also, the amount by which the pcs on bracket stabs need to be relocated limitPC: CARD _ 0, -- ObjectFiles.FileSegmentPC _ ObjectFiles.NoFileSegmentPC PJ CARD _ 0 one greater than last mentioned pc among the dbx stabs (note, code may actually reach higher pcs, but the pc of any function start will be < limitPC) dataReloc: CARD _ 0, -- data segment relocation for SunOS5.x firstStabX: CARD _ 0, limitStabX: CARD _ 0, -- all stabX lie in [firstStabX..limitStabX) outerBracket: BracketPair, stabs: REF StabSet _ NIL, staticVarsInstalled: BOOLEAN _ FALSE, versionStampStab: Stab, globalFrameStab: Stab, versionStampInfo: REF VersionStampInfo, globalFrameGvl: ObjectFiles.GlobalVarLoc, funStabsInstalled: BOOLEAN _ FALSE, funStabs: FunStabSet, fdIndex: INT32, pcToLineNum: PCtoLineNumMap, lineNumToPC: LineNumToPCMap]; StabRange: TYPE = RECORD[first, count: CARD]; StabSet: TYPE = RECORD[SEQUENCE nStabs: CARDINAL OF Stab]; FunStabSet: TYPE = REF FunStabSetBody; FunStabSetBody: TYPE = RECORD[firstX: CARD, funStabs: SEQUENCE nFunStabs: CARDINAL OF FunStabInfo]; FunStabInfo: TYPE = RECORD[ stab: Stab, firstX, count: CARD, --the X range of this fn firstLocal: Stab _ NIL, --of the Scan{Module,Fn}Structure protocol nextX: CARD, --of the Scan{Module,Fn}Structure protocol funHandle: FunHandle, bracketsScanned: BOOLEAN, brackets: BracketPair]; Header: TYPE = REF HeaderBody; HeaderBody: TYPE = RECORD[ dynamic: BOOL, -- bits [0..0] toolversion: BYTE, -- bits [1..7] machtype: BYTE, magic: CARD16, flags: CARD16 _ 0, text, iData, textReloc, dataReloc, symsReloc, syms, extSyms, auxSyms, debug, linno, fileDescr, procDescr: MemorySegmentInfo _ [0, 0], textLoadOffset: CARD32, bssSize: CARD32, entryPoint: CARD32, nPageSize: CARD32, nEntries, nExtEntries, nAuxEntries, nFileDescr, nProcDescr, nLinnoEntries: CARD32 _ 0, stringOffset, stringIndexLimit, extStringOffset, extStringIndexLimit: CARD32 _ 0, clientData: REF ANY _ NIL ]; MemorySegmentInfo: TYPE ~ RECORD [byteOffset, byteLength: CARD]; PCtoLineNumMap: TYPE = REF PCtoLineNumMapBody; PCtoLineNumMapBody: TYPE = RECORD[ SEQUENCE nSlines: CARDINAL OF SLineData]; LineNumToPCMap: TYPE = REF LineNumToPCMapBody; LineNumToPCMapBody: TYPE = RECORD[ SEQUENCE nSlines: CARDINAL OF SLineData]; SLineData: TYPE = RECORD[cLineNum: CARD, parsedRelPC: ObjectFiles.FileSegmentPC]; FunHandle: TYPE = REF FunHandleBody; FunHandleBody: TYPE = RECORD[ module: Module, index: CARD]; BracketPair: TYPE = REF BracketPairBody; BracketPairBody: TYPE = RECORD[ module: Module, kind: ObjectFiles.BracketPairKind, firstX, limitX: CARD, -- pair covers [firstX, limitX) firstPC, pcLimit: CARD, -- pair's instructions start in [firstPC, pcLimit) funStab: Stab, -- NIL if not a syntheticFun bracket pair funIndex: CARD, -- 0 for outermost bracket pair symbols: StabList, innerBrackets: LIST OF BracketPair]; -- in increasing numerical order ScanModuleStructure: PROC [module: Module, perFn: FnConsumer]; FnConsumer: TYPE ~ PROC [funStab: Stab, firstLocal: Stab _ NIL, nextX: CARD] RETURNS [limitX: CARD]; ScanFnStructure: FnFinisher; FnFinisher: TYPE ~ PROC [ module: Module, funStab: Stab, firstLocal: Stab _ NIL, nextX: CARD, perParm: PROC [Stab] _ NIL, perBracket: BracketConsumer _ NIL ] RETURNS [limitX, limitPc: CARD]; BracketConsumer: TYPE ~ PROC [first: Stab] RETURNS [limitX: CARD]; ScanBracketStructure: BracketFinisher; BracketFinisher: TYPE ~ PROC [ module: Module, funStab: Stab, first: Stab, perLocal: PROC [Stab] _ NIL, perSubBracket: BracketConsumer _ NIL ] RETURNS [limitX, firstPc, limitPc: CARD]; TranslationTable: TYPE ~ REF TranslationTableBody _ NIL; TranslationTableBody: TYPE ~ RECORD[ SEQUENCE length: CARD OF Translation]; Translation: TYPE ~ RECORD[ byteOffset, length, compareValue: CARD, format: ROPE, type: {point, first, middle, last} _ point]; ObjectFileFlavor: TYPE = REF ObjectFileFlavorBody _ NIL; ObjectFileFlavorBody: TYPE = RECORD[ formatSpecificString: ROPE, cGrammar: ObjectFiles.CGrammar, readHeaderProc: ReadHeaderProcType, moduleFromParsedAndPCProc: ModuleFromParsedAndPCProcType, varLocFromStabProc: VarLocFromStabProcType, getTypeRefProc: GetTypeRefProcType, installBracketPairsForOneFunStabProc: InstallBracketPairsForOneFunStabProcType _ NIL, scanModuleStructure: PROC [module: Module, perFn: FnConsumer] _ NIL, scanFnStructure: FnFinisher _ NIL, scanBktStructure: BracketFinisher _ NIL, fnsOrderedByStart: BOOL, installStaticVarsProc: InstallStaticVarsType, alterFunStabProc: AlterFunStabType, getSPOffsetProc: GetSPOffsetType]; AlterFunStabType: TYPE ~ PROC[module: Module, funStabX: CARD] RETURNS [Stab]; GetSPOffsetType: TYPE ~ PROC[module: Module, spc: ObjectFiles.FileSegmentPC] RETURNS [INT]; InstallStaticVarsType: TYPE ~ PROC[module: Module]; ReadHeaderProcType: TYPE ~ PROC[stream: IO.STREAM] RETURNS[Header]; ModuleFromParsedAndPCProcType: TYPE ~ PROC[whole: Parsed, spc: ObjectFiles.FileSegmentPC, moduleRope: ROPE _ NIL] RETURNS[Module]; VarLocFromStabProcType: TYPE ~ PROC [stab: Stab] RETURNS[ObjectFiles.VarLoc]; GetTypeRefProcType: TYPE ~ PROC[sourceStream:IO.STREAM] RETURNS [ROPE]; InstallBracketPairsForOneFunStabProcType: TYPE ~ PROC[module: Module, funStabIndex: CARD]; OFFFromStream: PROC[stream: IO.STREAM] RETURNS [ROPE]; RegisterObjectFileFlavor: PROC[flavor: ObjectFileFlavor, table: TranslationTable]; RetrieveObjectFileFlavor: PROC[formatSpecificString: ROPE] RETURNS[flavor: ObjectFileFlavor]; CheckStaticVar: PROC[stab: Stab, namePrefix: ROPE, allowSuffix: BOOL] RETURNS [ObjectFiles.VarLoc]; ScanSymbolStabs: PROC[module: Module, firstX: CARD, head, tail: StabList] RETURNS[--nextX-- CARD, --head, tail of collected symbols-- StabList, StabList]; ReadInitialDataAsRope: PROC[module: Module, fileByteOffset: CARD] RETURNS[ROPE]; ReadStabRope: PROC[stab: Stab] RETURNS [rope: ROPE]; ReadStab: PROC[module: Module, stabX: CARD] RETURNS[Stab]; RaiseUnreadableObjectFileForFun: PROC[msg: ROPE, module: Module, fun: Stab]; END.. Φ ObjectFilesPrivate.mesa Copyright Σ 1990, 1991, 1992 by Xerox Corporation. All rights reserved. Adapted from DotOAccessPrivate Laurie Horton, June 10, 1992 12:14 pm PDT Philip James, February 10, 1992 1:05 pm PST Katsuyuki Komatsu January 23, 1993 10:20 am PST Last tweaked by Mike Spreitzer January 21, 1993 4:41 pm PST Jas, January 5, 1993 11:11 am PST This definitions file contains the definitions of types that are exported from ObjectFilesPrivateImpl. The hope is that this will reduce exported type conflicts in the DMachine world. We begin with types defined in ObjectFiles. Next, the exported types And finally, types needed to define the exported types. sorted by PC sorted by Line Num Functions Bracket Pairs Parsing the sequence of Stabs in a Module Here is a parser for the sequence of Stabs in a Module. The grammar depends on the object file format, and is documented in CirioReverseEngineering.tioga for each object file format. This interface uses enumeration procedures that take callbacks, instead of procedures that return lists. The hypothesis is that the consumer of this parse can be common across all object file formats and live in ObjectFilesImpl, whereas the actual parser appears in each format-specific implementation. firstLocal is NIL if there are no local declarations. nextX is the X after the argument declarations, and =firstLocal.stabX if firstLocal isn't NIL. Must call ScanFnStructure exactly once, and return the limitX. Args 2-4 are those given to the FnConsumer. perParm, if not NIL, is called for each Stab that concerns a parameter. perBracket, if not NIL, is called some number of times. Must call ScanBracketStructure exactly once. Calls perLocal, if not NIL, for each local declaration Stab. Calls perSubBracket, if not NIL, for each bracket pair directly nested in this one. ObjectFile implementation registration Either installBracketPairsForOneFunStabProc is filled in or scanModuleStructure, scanFnStructure, & scanBktStructure are. Κ Λ•NewlineDelimiter ™codešœ™K™HK™K™)K™+K™/K™;K™!—K˜šΟk ˜ Kšœœœ˜Kšœ œY˜jKšœ œœ˜Kšœœœ˜Kšœœ ˜!—K˜K˜K˜KšΟnœœ œ˜(Kš˜K˜Kšœg™gK™PK™K™Kšœ+™+™Kšœœœ˜Kšœœ˜Kšœ œœœ˜Kšœœ ˜6—K˜K™˜Kšœœœ ˜šœ œœ˜Kšœ ˜ Kšœ œœ˜Kšœœ˜Kšœ˜Kšœ˜Jšœ œœœΟc˜-Kšœ œ˜Kšœ œœ ˜—Kšœœœ ˜šœ œœ˜Kšœ˜KšœœŸ˜*Kšœœ˜Kšœ œ˜Kšœ œŸJ˜]Kšœ œŸή˜ρKšœ œŸ'˜K˜š œ œœ$œ œœ œ˜dKšΟe œ+™5Kš‘œ/‘œ‘ œ‘œ™^Kšœ ‘œ‘œ™>—K˜Kšžœ ˜šœ œœ˜Kšœ˜Kšœ˜Kšœœ˜Kšœœ˜ Kšœ œ œ˜Kšœ˜!Kšœœœ˜"K™+Kš‘œ ‘œ4™GKš‘ œ ‘œ!™7—K˜š œœœœ œ˜BKšœ ‘œ™,—K˜Kšžœ˜&šœœœ˜Kšœ˜Kšœ˜Kšœ ˜ Kšœ œ œ˜Kšœ!˜$Kšœœœ˜+Kšœ‘œ ‘œ"™