Структура метки (первый блок) .TSK файла немного отличается между вариантом под M и под M-Plus (из за поддержки разделяемых библиотек режима супервизора). И из-за этого различия некоторые поля имеют разные смещения в зависимости от содержимого поля L$BSYS (4 для M-Plus). А сама структура метки - фиксированная по длине часть; переменная по длине часть; фиксированная по длине часть. И после некоторого размышления - получилось сделать описание и под такой вариант (своеобразный if else в аттрибутах):
Конструктор этого класса в старом варианте:Код:public class TaskLabel { [Map("L$BTSK: .BLKW 2", PDP11Type.Radix50)] public string TaskName; [Map("L$BPAR: .BLKW 2", PDP11Type.Radix50)] public string TaskPartitionName; [Map("L$BSA: .BLKW 1")] public UInt16 BaseAddress; [Map("L$BHGV: .BLKW 1")] public UInt16 HighestWin0VirtualAddress; [Map("L$BMXV: .BLKW 1")] public UInt16 HighestVirtualAddress; [Map("L$BLDZ: .BLKW 1")] public UInt16 LoadSizeIn64bBlocks; [Map("L$BMXZ: .BLKW 1")] public UInt16 MaximumSizeIn64bBlocks; [Map("L$BOFF: .BLKW 1")] public UInt16 OffsetIntoPartition; [Map("L$BWND: .BLKB 1")] public byte WindowBlocksCount; [Map("L$BSYS: .BLKB 1")] public byte SysID; [Map("L$BSEG: .BLKW 1")] public UInt16 SizeOfOverlaySegmentDescriptors; [Map("L$BFLG: .BLKW 1")] public TS_FLG Flags; public bool IsNoExternalHeader => ((Flags & TS_FLG.TS_NXH) != 0); public bool IsExternalHeader => ((Flags & TS_FLG.TS_XHR) != 0); public bool IsPriviledge => ((Flags & TS_FLG.TS_PRV) != 0); public bool IsDoesNotMapIOPage => ((Flags & TS_FLG.TS_IOP) != 0); public bool IsCheckpointable => ((Flags & TS_FLG.TS_CHK) != 0); public bool IsInCompatabilityMode => ((Flags & TS_FLG.TS_CMP) != 0); public bool IsNoSend => ((Flags & TS_FLG.TS_NSD) != 0); public bool IsSlaveTask => ((Flags & TS_FLG.TS_SLV) != 0); public bool IsGeneratesPostmortDump => ((Flags & TS_FLG.TS_PMD) != 0); public bool IsAncillaryControlProcessor => ((Flags & TS_FLG.TS_ACP) != 0); public bool IsNoHeader => ((Flags & TS_FLG.TS_NHD) != 0); public bool IsPositionIndependentCode => ((Flags & TS_FLG.TS_PIC) != 0); [Map("L$BDAT: .BLKW 3")] public RSXDate CreationDate; [Map("L$BLIB: .BLKW ?L$BSYS:=4:15:7")] public SharedRegion[] SharedRegions; [Map("L$SOME: .BLKW 1")] public UInt16 Some; [Map("L$BPRI: .BLKW 1")] public UInt16 Priority; [Map("L$BXFR: .BLKW 1")] public UInt16 TransferAddress; [Map("L$BEXT: .BLKW 1")] public UInt16 TaskExtension; [Map("L$BSGL: .BLKW 1")] public UInt16 SegmentLoadListBlockNumber; [Map("L$BHRB: .BLKW 1")] public UInt16 HeaderBlockNumber; [Map("L$BBLK: .BLKW 1")] public UInt16 LabelBlockCount; [Map("L$BLUN: .BLKW 1")] public UInt16 LUNCount; [Map("L$BROB: .BLKW 1")] public UInt16 ROImageRelativeBlockNumber; [Map("L$BROL: .BLKW 1")] public UInt16 ROImageLoadSize; [Map("L$BRDL: .BLKW 1")] public UInt16 RODataSizeIn64bBlocks; [Map("L$BHDB: .BLKW 1")] public UInt16 DataHeaderRelativeBlockNumber; [Map("L$BDHV: .BLKW 1")] public UInt16 DataWin1HighVirtualAddress; [Map("L$BDMV: .BLKW 1")] public UInt16 DataHighVirtualAddress; [Map("L$BDLZ: .BLKW 1")] public UInt16 DataLoadSize; [Map("L$BDMZ: .BLKW 1")] public UInt16 DataMaxSize; [Map("L$BAPR: .BLKW 1")] public UInt16 BAPR; // ?? [Set(".=772")] [Map("L$BFL2: .BLKW 1")] public static TS_FLG2 Flags2; [Map("L$BLRL: .BLKW 1")] public UInt16 BLRL; // ?? [Map("L$AME: .BLKW 1")] public UInt16 AME; // ?? [Set(".=1000")] [Map("L$BASG:")] public static UInt16 Length; ...
и в новом:Код:public TaskLabel(byte[] data, uint baseOffset = 0) { TaskName = data.GetDWord(LBLDF.L_BTSK).Radix50().Trim(); TaskPartitionName = data.GetDWord(LBLDF.L_BPAR).Radix50().Trim(); BaseAddress = data.GetWord(LBLDF.L_BSA); HighestWin0VirtualAddress = data.GetWord(LBLDF.L_BHGV); HighestVirtualAddress = data.GetWord(LBLDF.L_BMXV); LoadSizeIn64bBlocks = data.GetWord(LBLDF.L_BLDZ); MaximumSizeIn64bBlocks = data.GetWord(LBLDF.L_BMXZ); OffsetIntoPartition = data.GetWord(LBLDF.L_BOFF); WindowBlocksCount = data[LBLDF.L_BWND]; SysID = data[LBLDF.L_BSYS]; SizeOfOverlaySegmentDescriptors = data.GetWord(LBLDF.L_BSEG); Flags = (TS_FLG)data.GetWord(LBLDF.L_BFLG); CreationDate = new RSXDate(data.GetTWord(LBLDF.L_BDAT)); UInt16 currPtr = LBLDF.L_BLIB; int maxCnt = SysID == 4? 15 : 7; int commonCnt = 0; while ((maxCnt > 0) && (data.GetWord(currPtr) != 0)) { maxCnt--; commonCnt++; currPtr += (UInt16)typeof(SharedRegion).GetOffset("R$LSIZ"); } if ((maxCnt == 0) && (data.GetWord(currPtr) != 0)) throw new FormatException("Error in task label"); commonCnt = WindowBlocksCount; SharedRegions = new SharedRegion[commonCnt]; UInt16 R_LSIZ = (UInt16)typeof(SharedRegion).GetOffset("R$LSIZ"); for (int idx=0; idx<commonCnt; idx++) { SharedRegions[idx] = new(data, (uint)(LBLDF.L_BLIB + idx * R_LSIZ)); } if (SysID == 4) { Priority = data.GetWord(LBLDF.L_BPRI_MP); TransferAddress = data.GetWord(LBLDF.L_BXFR_MP); TaskExtension = data.GetWord(LBLDF.L_BEXT_MP); SegmentLoadListBlockNumber = data.GetWord(LBLDF.L_BSGL_MP); HeaderBlockNumber = data.GetWord(LBLDF.L_BHRB_MP); LabelBlockCount = data.GetWord(LBLDF.L_BBLK_MP); LUNCount = data.GetWord(LBLDF.L_BLUN_MP); ROImageRelativeBlockNumber = data.GetWord(LBLDF.L_BROB_MP); ROImageLoadSize = data.GetWord(LBLDF.L_BROL_MP); RODataSizeIn64bBlocks = data.GetWord(LBLDF.L_BRDL_MP); DataHeaderRelativeBlockNumber = data.GetWord(LBLDF.L_BHDB_MP); DataWin1HighVirtualAddress = data.GetWord(LBLDF.L_BDHV_MP); DataHighVirtualAddress = data.GetWord(LBLDF.L_BDMV_MP); DataLoadSize = data.GetWord(LBLDF.L_BDLZ_MP); DataMaxSize = data.GetWord(LBLDF.L_BDMZ_MP); BAPR = data.GetWord(LBLDF.L_BAPR_MP); // ?? } else { Priority = data.GetWord(LBLDF.L_BPRI); TransferAddress = data.GetWord(LBLDF.L_BXFR); TaskExtension = data.GetWord(LBLDF.L_BEXT); SegmentLoadListBlockNumber = data.GetWord(LBLDF.L_BSGL); HeaderBlockNumber = data.GetWord(LBLDF.L_BHRB); LabelBlockCount = data.GetWord(LBLDF.L_BBLK); LUNCount = data.GetWord(LBLDF.L_BLUN); ROImageRelativeBlockNumber = data.GetWord(LBLDF.L_BROB); ROImageLoadSize = data.GetWord(LBLDF.L_BROL); RODataSizeIn64bBlocks = data.GetWord(LBLDF.L_BRDL); DataHeaderRelativeBlockNumber = data.GetWord(LBLDF.L_BHDB); DataWin1HighVirtualAddress = data.GetWord(LBLDF.L_BDHV); DataHighVirtualAddress = data.GetWord(LBLDF.L_BDMV); DataLoadSize = data.GetWord(LBLDF.L_BDLZ); DataMaxSize = data.GetWord(LBLDF.L_BDMZ); BAPR = data.GetWord(LBLDF.L_BAPR); // ?? } }
Безусловно, Mapper был дописан для поддержки нового описания в MapКод:public TaskLabel(byte[] data) { this.Mapper<TaskLabel>(data); }И доделка предполагает и несколько более сложные варианты - несколько вариантов длины блока переменной длины. И блок может быть не один. В целом же - доделка пока идёт по принципу - налетим на что то ещё в макросах - подпилим Mapper
Осталось подумать над работой с флагами![]()




И доделка предполагает и несколько более сложные варианты - несколько вариантов длины блока переменной длины. И блок может быть не один. В целом же - доделка пока идёт по принципу - налетим на что то ещё в макросах - подпилим Mapper
Ответить с цитированием
Размещение рекламы на форуме способствует его дальнейшему развитию 
