fpdesk.pas 32 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164
  1. {
  2. This file is part of the Free Pascal Integrated Development Environment
  3. Copyright (c) 1998 by Berczi Gabor
  4. Desktop loading/saving routines
  5. See the file COPYING.FPC, included in this distribution,
  6. for details about the copyright.
  7. This program is distributed in the hope that it will be useful,
  8. but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  10. **********************************************************************}
  11. unit FPDesk;
  12. {$H-}
  13. interface
  14. const
  15. MinDesktopVersion = $000A;
  16. DesktopVersion = $000A; { <- if you change any Load&Store methods,
  17. default object properties (Options,State)
  18. then you should also change this }
  19. ResDesktopFlags = 'FLAGS';
  20. ResVideo = 'VIDEOMODE';
  21. ResHistory = 'HISTORY';
  22. ResClipboard = 'CLIPBOARD';
  23. ResWatches = 'WATCHES';
  24. ResBreakpoints = 'BREAKPOINTS';
  25. ResDesktop = 'DESKTOP';
  26. ResSymbols = 'SYMBOLS';
  27. ResCodeComplete = 'CODECOMPLETE';
  28. ResCodeTemplates = 'CODETEMPLATES';
  29. ResLastDirectory = 'LASTDIRECTORY';
  30. ResKeys = 'KEYS';
  31. procedure InitDesktopFile;
  32. function LoadDesktop: boolean;
  33. function SaveDesktop: boolean;
  34. procedure DoneDesktopFile;
  35. function WriteSymbolsFile(const filename : string): boolean;
  36. function ReadSymbolsFile(const filename : string): boolean;
  37. implementation
  38. uses Dos,
  39. Objects,Drivers,
  40. Video,
  41. Views,App,HistList,BrowCol,
  42. WUtils,WResourc,WViews,WEditor,
  43. fpdebug, wcedit,
  44. {$ifdef Unix}
  45. FPKeys,
  46. {$endif Unix}
  47. FPConst,FPVars,FPTools,FPUtils,FPViews,FPHelp,
  48. FPCompil,FPCodCmp,FPCodTmp;
  49. type
  50. TWindowInfo =
  51. {$ifndef FPC_REQUIRES_PROPER_ALIGNMENT}
  52. packed
  53. {$endif FPC_REQUIRES_PROPER_ALIGNMENT}
  54. record
  55. HelpCtx : word;
  56. Bounds : TRect;
  57. Visible : boolean;
  58. WinNb : byte;
  59. ExtraDataSize : word;
  60. TitleLen : word;
  61. Title : packed record end;
  62. end;
  63. {$ifdef useresstrings}
  64. resourcestring
  65. {$else}
  66. const
  67. {$endif}
  68. { Desktop file messages }
  69. msg_readingdesktopfile = 'Reading desktop file...';
  70. msg_writingdesktopfile = 'Writing desktop file...';
  71. msg_readingdesktopcontents = 'Reading desktop contents...';
  72. msg_storingdesktopcontents = 'Storing desktop contents...';
  73. msg_readinghistory = 'Reading history...';
  74. msg_storinghistory = 'Storing history...';
  75. msg_readingwatches = 'Reading watches...';
  76. msg_storingwatches = 'Storing watches...';
  77. msg_readingbreakpoints = 'Reading breakpoints...';
  78. msg_storingbreakpoints = 'Storing breakpoints...';
  79. msg_readingcodecompletewordlist = 'Reading CodeComplete wordlist...';
  80. msg_storingcodecompletewordlist = 'Writing CodeComplete wordlist...';
  81. msg_readingcodetemplates = 'Reading CodeTemplates...';
  82. msg_storingcodetemplates = 'Writing CodeTemplates...';
  83. msg_readingreturntolastdir = 'Reading Last directory to return...';
  84. msg_storingreturntolastdir = 'Writing Last directory to return...';
  85. msg_readingsymbolinformation = 'Reading symbol information...';
  86. msg_storingsymbolinformation = 'Storing symbol information...';
  87. msg_failedtoreplacedesktopfile = 'Failed to replace desktop file.';
  88. msg_errorloadinghistory = 'Error loading history';
  89. msg_errorstoringhistory = 'Error storing history';
  90. msg_errorloadingkeys = 'Error loading custom keys';
  91. msg_errorstoringkeys = 'Error storing custom keys';
  92. msg_errorloadingwatches = 'Error loading watches';
  93. msg_errorstoringwatches = 'Error storing watches';
  94. msg_errorloadingbreakpoints = 'Error loading breakpoints';
  95. msg_errorstoringbreakpoints = 'Error storing breakpoints';
  96. msg_errorloadingdesktop = 'Error loading desktop';
  97. msg_errorstoringdesktop = 'Error storing desktop';
  98. msg_errorreadingflags = 'Error loading flags';
  99. msg_errorwritingflags = 'Error writing flags';
  100. msg_errorreadingvideomode = 'Error reading video mode';
  101. msg_errorstoringvideomode = 'Error storing video mode';
  102. msg_errorloadingcodetemplates = 'Error loading CodeTemplates';
  103. msg_errorstoringcodetemplates = 'Error writing CodeTemplates';
  104. msg_errorloadingreturntolastdir = 'Error loading Last directory to return';
  105. msg_errorstoringreturntolastdir = 'Error writing Last directory to return';
  106. msg_errorloadingsymbolinformation = 'Error loading symbol information';
  107. msg_errorstoringsymbolinformation = 'Error storing symbol information';
  108. msg_errorloadingcodecompletewordlist = 'Error loading CodeComplete wordlist';
  109. msg_errorstoringcodecompletewordlist = 'Error writing CodeComplete wordlist';
  110. msg_invaliddesktopversionlayoutlost = 'Invalid desktop version. Desktop layout lost.';
  111. msg_saveansifile = 'Save previous screen as Ansi File';
  112. msg_click_upper_left = 'Click to select upper left corner; Escape to cancel; Enter to select (0,0)';
  113. msg_click_lower_right = 'Click to select lower right corner; Escape to cancel; Enter to select (maxX,maxY)';
  114. msg_cantopenfile = 'Can''t open %s';
  115. msg_cantcreatefile = 'Can''t create %s';
  116. msg_cantfindfile = 'Can''t find %s';
  117. msg_errorreadingfile = 'Error reading file %s';
  118. msg_loadingfile = 'Loading %s';
  119. msg_storingfile = 'Storing %s';
  120. msg_closingfile = 'Closing %s';
  121. msg_openingsourcefile = 'Opening source file... (%s)';
  122. msg_readingfileineditor = 'Reading %s into editor...';
  123. procedure InitDesktopFile;
  124. begin
  125. if DesktopLocation=dlCurrentDir then
  126. DesktopPath:=FExpand(DesktopFileName)
  127. else
  128. DesktopPath:=FExpand(DirOf(IniFilePath)+DesktopFileName);
  129. end;
  130. procedure DoneDesktopFile;
  131. begin
  132. end;
  133. function ReadHistory(F: PResourceFile): boolean;
  134. var S: PMemoryStream;
  135. OK: boolean;
  136. begin
  137. PushStatus(msg_readinghistory);
  138. New(S, Init(32*1024,4096));
  139. OK:=F^.ReadResourceEntryToStream(resHistory,langDefault,S^);
  140. S^.Seek(0);
  141. if OK then
  142. LoadHistory(S^);
  143. Dispose(S, Done);
  144. if OK=false then
  145. ErrorBox(msg_errorloadinghistory,nil);
  146. PopStatus;
  147. ReadHistory:=OK;
  148. end;
  149. function WriteHistory(F: PResourceFile): boolean;
  150. var S: PMemoryStream;
  151. OK: boolean;
  152. begin
  153. PushStatus(msg_storinghistory);
  154. New(S, Init(10*1024,4096));
  155. StoreHistory(S^);
  156. S^.Seek(0);
  157. F^.CreateResource(resHistory,rcBinary,0);
  158. OK:=F^.AddResourceEntryFromStream(resHistory,langDefault,0,S^,S^.GetSize);
  159. Dispose(S, Done);
  160. if OK=false then
  161. ErrorBox(msg_errorstoringhistory,nil);
  162. PopStatus;
  163. WriteHistory:=OK;
  164. end;
  165. {$ifdef Unix}
  166. function ReadKeys(F: PResourceFile): boolean;
  167. var S: PMemoryStream;
  168. OK: boolean;
  169. begin
  170. New(S, Init(32*1024,4096));
  171. OK:=F^.ReadResourceEntryToStream(resKeys,langDefault,S^);
  172. S^.Seek(0);
  173. if OK then
  174. LoadKeys(S^);
  175. Dispose(S, Done);
  176. if OK=false then
  177. ErrorBox(msg_errorloadingkeys,nil);
  178. ReadKeys:=OK;
  179. end;
  180. function WriteKeys(F: PResourceFile): boolean;
  181. var S: PMemoryStream;
  182. OK: boolean;
  183. begin
  184. New(S, Init(10*1024,4096));
  185. StoreKeys(S^);
  186. S^.Seek(0);
  187. F^.CreateResource(resKeys,rcBinary,0);
  188. OK:=F^.AddResourceEntryFromStream(resKeys,langDefault,0,S^,S^.GetSize);
  189. Dispose(S, Done);
  190. if OK=false then
  191. ErrorBox(msg_errorstoringkeys,nil);
  192. WriteKeys:=OK;
  193. end;
  194. {$endif Unix}
  195. (*function ReadClipboard(F: PResourceFile): boolean;
  196. begin
  197. ReadClipboard:=true;
  198. end;
  199. function WriteClipboard(F: PResourceFile): boolean;
  200. var S: PMemoryStream;
  201. begin
  202. if Assigned(Clipboard) then
  203. begin
  204. PushStatus('Storing clipboard content...');
  205. New(S, Init(10*1024,4096));
  206. Clipboard^.SaveToStream(S^);
  207. S^.Seek(0);
  208. F^.CreateResource(resClipboard,rcBinary,0);
  209. F^.AddResourceEntryFromStream(resClipboard,langDefault,0,S^,S^.GetSize);
  210. Dispose(S, Done);
  211. PopStatus;
  212. end;
  213. WriteClipboard:=true;
  214. end;*)
  215. function ReadWatches(F: PResourceFile): boolean;
  216. {$ifndef NODEBUG}
  217. var S: PMemoryStream;
  218. OK: boolean;
  219. OWC : PWatchesCollection;
  220. {$endif}
  221. begin
  222. {$ifndef NODEBUG}
  223. PushStatus(msg_readingwatches);
  224. New(S, Init(32*1024,4096));
  225. OK:=F^.ReadResourceEntryToStream(resWatches,langDefault,S^);
  226. S^.Seek(0);
  227. if OK then
  228. begin
  229. OWC:=WatchesCollection;
  230. WatchesCollection:=PWatchesCollection(S^.Get);
  231. OK:=(S^.Status=stOK);
  232. if OK and assigned(OWC) and assigned(WatchesCollection) then
  233. Dispose(OWC,Done)
  234. else if assigned(OWC) then
  235. WatchesCollection:=OWC;
  236. end;
  237. if OK=false then
  238. ErrorBox(msg_errorloadingwatches,nil);
  239. ReadWatches:=OK;
  240. Dispose(S, Done);
  241. PopStatus;
  242. {$else NODEBUG}
  243. ReadWatches:=true;
  244. {$endif NODEBUG}
  245. end;
  246. function WriteWatches(F: PResourceFile): boolean;
  247. var
  248. S : PMemoryStream;
  249. OK : boolean;
  250. begin
  251. {$ifndef NODEBUG}
  252. if not assigned(WatchesCollection) then
  253. {$endif NODEBUG}
  254. WriteWatches:=true
  255. {$ifndef NODEBUG}
  256. else
  257. begin
  258. PushStatus(msg_storingwatches);
  259. New(S, Init(30*1024,4096));
  260. S^.Put(WatchesCollection);
  261. S^.Seek(0);
  262. F^.CreateResource(resWatches,rcBinary,0);
  263. OK:=F^.AddResourceEntryFromStream(resWatches,langDefault,0,S^,S^.GetSize);
  264. Dispose(S, Done);
  265. if OK=false then
  266. ErrorBox(msg_errorstoringwatches,nil);
  267. PopStatus;
  268. WriteWatches:=OK;
  269. end;
  270. {$endif NODEBUG}
  271. end;
  272. function ReadBreakpoints(F: PResourceFile): boolean;
  273. {$ifndef NODEBUG}
  274. var S: PMemoryStream;
  275. OK: boolean;
  276. OBC : PBreakpointCollection;
  277. {$endif}
  278. begin
  279. {$ifndef NODEBUG}
  280. PushStatus(msg_readingbreakpoints);
  281. New(S, Init(32*1024,4096));
  282. OK:=F^.ReadResourceEntryToStream(resBreakpoints,langDefault,S^);
  283. S^.Seek(0);
  284. if OK then
  285. begin
  286. OBC:=BreakpointsCollection;
  287. BreakpointsCollection:=PBreakpointCollection(S^.get);
  288. OK:=(S^.Status=stOK);
  289. If OK and assigned(OBC) and assigned(BreakpointsCollection) then
  290. Begin
  291. Dispose(OBC,Done);
  292. BreakpointsCollection^.ShowAllBreakpoints;
  293. end
  294. else if assigned(OBC) then
  295. BreakpointsCollection:=OBC;
  296. end;
  297. if OK=false then
  298. ErrorBox(msg_errorloadingbreakpoints,nil);
  299. ReadBreakpoints:=OK;
  300. Dispose(S, Done);
  301. PopStatus;
  302. {$else NODEBUG}
  303. ReadBreakpoints:=true;
  304. {$endif NODEBUG}
  305. end;
  306. function WriteBreakpoints(F: PResourceFile): boolean;
  307. var
  308. S : PMemoryStream;
  309. OK : boolean;
  310. begin
  311. {$ifndef NODEBUG}
  312. if not assigned(BreakpointsCollection) then
  313. {$endif NODEBUG}
  314. WriteBreakPoints:=true
  315. {$ifndef NODEBUG}
  316. else
  317. begin
  318. PushStatus(msg_storingbreakpoints);
  319. New(S, Init(30*1024,4096));
  320. S^.Put(BreakpointsCollection);
  321. S^.Seek(0);
  322. F^.CreateResource(resBreakpoints,rcBinary,0);
  323. OK:=F^.AddResourceEntryFromStream(resBreakpoints,langDefault,0,S^,S^.GetSize);
  324. Dispose(S, Done);
  325. if OK=false then
  326. ErrorBox(msg_errorstoringbreakpoints,nil);
  327. WriteBreakPoints:=OK;
  328. PopStatus;
  329. end;
  330. {$endif NODEBUG}
  331. end;
  332. function DeskUseSyntaxHighlight(Editor: PFileEditor): boolean;
  333. var b : boolean;
  334. begin
  335. b:= (*(Editor^.IsFlagSet(efSyntaxHighlight)) and *) ((Editor^.FileName='') or
  336. MatchesMaskList(NameAndExtOf(Editor^.FileName),HighlightExts));
  337. DeskUseSyntaxHighlight:=b;
  338. end;
  339. function ReadVideoMode(F: PResourceFile;var NewScreenMode : TVideoMode): boolean; forward;
  340. function ReadOpenWindows(F: PResourceFile): boolean;
  341. var S: PMemoryStream;
  342. OK: boolean;
  343. DV: word;
  344. WI: TWindowInfo;
  345. VM: TVideoMode;
  346. Title: string;
  347. XDataOfs: word;
  348. XData: array[0..1024] of byte;
  349. procedure GetData(var B; Size: word);
  350. begin
  351. if Size>0 Then
  352. Begin
  353. Move(XData[XDataOfs],B,Size);
  354. Inc(XDataOfs,Size);
  355. End;
  356. end;
  357. procedure ProcessWindowInfo;
  358. var W: PWindow;
  359. SW: PSourceWindow absolute W;
  360. St: string;
  361. Ch: AnsiChar;
  362. TP,TP2: TPoint;
  363. L: longint;
  364. R: TRect;
  365. ZZ: byte;
  366. Z: TRect;
  367. Len : Byte;
  368. BM: TEditorBookMark;
  369. begin
  370. XDataOfs:=0;
  371. Desktop^.Lock;
  372. W:=SearchWindow(Title);
  373. case WI.HelpCtx of
  374. hcSourceWindow :
  375. begin
  376. GetData(len,1);
  377. SetLength(St,Len);
  378. GetData(St[1],Len);
  379. W:=ITryToOpenFile(@WI.Bounds,St,0,0,false,false,true);
  380. if Assigned(W)=false then
  381. begin
  382. ClearFormatParams;
  383. AddFormatParamStr(St);
  384. Desktop^.Unlock;
  385. ErrorBox(msg_cantopenfile,@FormatParams);
  386. Desktop^.Lock;
  387. end
  388. else
  389. begin
  390. GetData(L,sizeof(L));
  391. If DeskUseSyntaxHighlight(SW^.Editor) Then
  392. L:=L or efSyntaxHighlight
  393. else
  394. L:=L and not efSyntaxHighlight;
  395. SW^.Editor^.SetFlags(L);
  396. GetData(TP,sizeof(TP)); GetData(TP2,sizeof(TP2));
  397. SW^.Editor^.SetSelection(TP,TP2);
  398. GetData(TP,sizeof(TP)); SW^.Editor^.SetCurPtr(TP.X,TP.Y);
  399. GetData(TP,sizeof(TP)); SW^.Editor^.ScrollTo(TP.X,TP.Y);
  400. for L:=0 to 9 do begin
  401. GetData(BM,Sizeof(BM));
  402. SW^.Editor^.SetBookmark(L,BM); {restore bookmarks}
  403. end;
  404. end;
  405. end;
  406. hcClipboardWindow:
  407. W:=ClipboardWindow;
  408. hcCalcWindow:
  409. W:=CalcWindow;
  410. hcMessagesWindow:
  411. begin
  412. if MessagesWindow=nil then
  413. Desktop^.Insert(New(PMessagesWindow, Init));
  414. W:=MessagesWindow;
  415. end;
  416. hcCompilerMessagesWindow:
  417. W:=CompilerMessageWindow;
  418. {$ifndef NODEBUG}
  419. hcGDBWindow:
  420. begin
  421. InitGDBWindow;
  422. W:=GDBWindow;
  423. end;
  424. hcDisassemblyWindow:
  425. begin
  426. InitDisassemblyWindow;
  427. W:=DisassemblyWindow;
  428. end;
  429. hcWatchesWindow:
  430. begin
  431. if WatchesWindow=nil then
  432. begin
  433. New(WatchesWindow,Init);
  434. Desktop^.Insert(WatchesWindow);
  435. end;
  436. W:=WatchesWindow;
  437. end;
  438. hcStackWindow:
  439. begin
  440. if StackWindow=nil then
  441. begin
  442. New(StackWindow,Init);
  443. Desktop^.Insert(StackWindow);
  444. end;
  445. W:=StackWindow;
  446. end;
  447. hcFPURegisters:
  448. begin
  449. if FPUWindow=nil then
  450. begin
  451. New(FPUWindow,Init);
  452. Desktop^.Insert(FPUWindow);
  453. end;
  454. W:=FPUWindow;
  455. end;
  456. hcVectorRegisters:
  457. begin
  458. if VectorWindow=nil then
  459. begin
  460. New(VectorWindow,Init);
  461. Desktop^.Insert(VectorWindow);
  462. end;
  463. W:=VectorWindow;
  464. end;
  465. hcRegistersWindow:
  466. begin
  467. if RegistersWindow=nil then
  468. begin
  469. New(RegistersWindow,Init);
  470. Desktop^.Insert(RegistersWindow);
  471. end;
  472. W:=RegistersWindow;
  473. end;
  474. hcBreakpointListWindow:
  475. begin
  476. if BreakpointsWindow=nil then
  477. begin
  478. New(BreakpointsWindow,Init);
  479. Desktop^.Insert(BreakpointsWindow);
  480. end;
  481. W:=BreakpointsWindow;
  482. end;
  483. {$endif NODEBUG}
  484. hcASCIITableWindow:
  485. begin
  486. if ASCIIChart=nil then
  487. begin
  488. New(ASCIIChart, Init);
  489. Desktop^.Insert(ASCIIChart);
  490. end;
  491. W:=ASCIIChart;
  492. if DV>=$A then
  493. begin
  494. GetData(ch,sizeof(AnsiChar));
  495. AsciiChart^.Report^.AsciiChar:=ord(ch);
  496. AsciiChart^.Table^.SetCursor(
  497. ord(ch) mod AsciiChart^.Table^.Size.X,
  498. ord(ch) div AsciiChart^.Table^.Size.X);
  499. end;
  500. end;
  501. end;
  502. if W=nil then
  503. begin
  504. Desktop^.Unlock;
  505. Exit;
  506. end;
  507. {calculate new location and size of window}
  508. if (VM.col > 0) and (ScreenWidth<>VM.col) then
  509. begin
  510. WI.Bounds.A.X:=round(WI.Bounds.A.X*ScreenWidth/VM.col);
  511. if (W^.Flags and wfGrow)<>0 then
  512. WI.Bounds.B.X:=Max(16,round(WI.Bounds.B.X*ScreenWidth/VM.col));
  513. end;
  514. if (VM.row > 2) and (ScreenHeight<>VM.row) then
  515. begin
  516. WI.Bounds.A.Y:=round(WI.Bounds.A.Y*(ScreenHeight-2)/(VM.row-2));
  517. if (W^.Flags and wfGrow)<>0 then
  518. WI.Bounds.B.Y:=Max(6,round(WI.Bounds.B.Y*(ScreenHeight-2)/(VM.row-2)));
  519. end;
  520. {relocat and resize window as needed}
  521. W^.GetBounds(R);
  522. if (R.A.X<>WI.Bounds.A.X) or (R.A.Y<>WI.Bounds.A.Y) then
  523. R.Move(WI.Bounds.A.X-R.A.X,WI.Bounds.A.Y-R.A.Y);
  524. if (W^.Flags and wfGrow)<>0 then
  525. begin
  526. R.B.X:=R.A.X+(WI.Bounds.B.X-WI.Bounds.A.X);
  527. R.B.Y:=R.A.Y+(WI.Bounds.B.Y-WI.Bounds.A.Y);
  528. end;
  529. W^.Locate(R);
  530. if W^.GetState(sfVisible)<>WI.Visible then
  531. if WI.Visible then
  532. begin
  533. W^.Show;
  534. W^.MakeFirst;
  535. end
  536. else
  537. W^.Hide;
  538. {check if window is out screen bounds and bring it back if so}
  539. ZZ:=0;
  540. Desktop^.GetExtent(Z);
  541. if R.A.Y>Z.B.Y-7 then
  542. begin
  543. R.A.Y:=Z.B.Y-7;
  544. ZZ:=1;
  545. end;
  546. if R.A.X>Z.B.X-4 then
  547. begin
  548. R.A.X:=Z.B.X-4;
  549. ZZ:=1;
  550. end;
  551. if R.A.Y<0 then
  552. begin
  553. R.A.Y:=0;
  554. ZZ:=1;
  555. end;
  556. if R.A.X<0 then
  557. begin
  558. R.A.X:=0;
  559. ZZ:=1;
  560. end;
  561. if ZZ<>0 then W^.MoveTo(R.A.X,R.A.Y);
  562. W^.Number:=WI.WinNb;
  563. Desktop^.Unlock;
  564. end;
  565. begin
  566. PushStatus(msg_readingdesktopcontents);
  567. OK:=ReadVideoMode(F,VM); {read video mode again (need old Hight and Width)}
  568. New(S, Init(32*1024,4096));
  569. OK:=F^.ReadResourceEntryToStream(resDesktop,langDefault,S^);
  570. S^.Seek(0);
  571. if OK then
  572. begin
  573. S^.Read(DV,SizeOf(DV));
  574. OK:=(DV=DesktopVersion) or (DV>=MinDesktopVersion);
  575. if OK=false then
  576. ErrorBox(msg_invaliddesktopversionlayoutlost,nil);
  577. end;
  578. if OK then
  579. begin
  580. XDataOfs:=0;
  581. repeat
  582. S^.Read(WI,sizeof(WI));
  583. if S^.Status=stOK then
  584. begin
  585. SetLength(Title,WI.TitleLen);
  586. S^.Read(Title[1],WI.TitleLen);
  587. FillChar(XData,SizeOf(XData),0);
  588. if WI.ExtraDataSize>0 then
  589. S^.Read(XData,WI.ExtraDataSize);
  590. ProcessWindowInfo;
  591. end;
  592. until (S^.Status<>stOK) or (S^.GetPos=S^.GetSize);
  593. (* TempDesk:=PFPDesktop(S^.Get);
  594. OK:=Assigned(TempDesk);
  595. if OK then
  596. begin
  597. Dispose(Desktop, Done);
  598. Desktop:=TempDesk;
  599. with Desktop^ do
  600. begin
  601. GetSubViewPtr(S^,CompilerMessageWindow);
  602. GetSubViewPtr(S^,CompilerStatusDialog);
  603. GetSubViewPtr(S^,ClipboardWindow);
  604. if Assigned(ClipboardWindow) then Clipboard:=ClipboardWindow^.Editor;
  605. GetSubViewPtr(S^,CalcWindow);
  606. GetSubViewPtr(S^,GDBWindow);
  607. GetSubViewPtr(S^,BreakpointsWindow);
  608. GetSubViewPtr(S^,WatchesWindow);
  609. GetSubViewPtr(S^,UserScreenWindow);
  610. GetSubViewPtr(S^,ASCIIChart);
  611. GetSubViewPtr(S^,MessagesWindow); LastToolMessageFocused:=nil;
  612. end;
  613. Application^.GetExtent(R);
  614. Inc(R.A.Y);Dec(R.B.Y);
  615. DeskTop^.Locate(R);
  616. Application^.Insert(Desktop);
  617. Desktop^.ReDraw;
  618. Message(Application,evBroadcast,cmUpdate,nil);
  619. end;*)
  620. if OK=false then
  621. ErrorBox(msg_errorloadingdesktop,nil);
  622. end;
  623. Dispose(S, Done);
  624. PopStatus;
  625. ReadOpenWindows:=OK;
  626. end;
  627. function WriteOpenWindows(F: PResourceFile): boolean;
  628. var S: PMemoryStream;
  629. procedure CollectInfo(P: PView);
  630. var W: PWindow;
  631. SW: PSourceWindow absolute W;
  632. WI: TWindowInfo;
  633. Title: string;
  634. XDataOfs: word;
  635. XData: array[0..1024] of byte;
  636. St: string;
  637. Ch: AnsiChar;
  638. TP: TPoint;
  639. BM: TEditorBookMark;
  640. L: longint;
  641. procedure AddData(const B; Size: word);
  642. begin
  643. Move(B,XData[XDataOfs],Size);
  644. Inc(XDataOfs,Size);
  645. end;
  646. begin
  647. XDataOfs:=0;
  648. W:=nil;
  649. if (P^.HelpCtx=hcSourceWindow) or
  650. (P^.HelpCtx=hcHelpWindow) or
  651. (P^.HelpCtx=hcClipboardWindow) or
  652. (P^.HelpCtx=hcCalcWindow) or
  653. (P^.HelpCtx=hcInfoWindow) or
  654. (P^.HelpCtx=hcBrowserWindow) or
  655. (P^.HelpCtx=hcMessagesWindow) or
  656. (P^.HelpCtx=hcCompilerMessagesWindow) or
  657. (P^.HelpCtx=hcGDBWindow) or
  658. (P^.HelpCtx=hcDisassemblyWindow) or
  659. (P^.HelpCtx=hcStackWindow) or
  660. (P^.HelpCtx=hcRegistersWindow) or
  661. (P^.HelpCtx=hcFPURegisters) or
  662. (P^.HelpCtx=hcVectorRegisters) or
  663. (P^.HelpCtx=hcWatchesWindow) or
  664. (P^.HelpCtx=hcBreakpointListWindow) or
  665. (P^.HelpCtx=hcASCIITableWindow)
  666. then
  667. W:=PWindow(P);
  668. if Assigned(W) and (P^.HelpCtx=hcSourceWindow) then
  669. if SW^.Editor^.FileName='' then
  670. W:=nil;
  671. if W=nil then Exit;
  672. FillChar(WI,sizeof(WI),0);
  673. Title:=W^.GetTitle(255);
  674. WI.HelpCtx:=W^.HelpCtx;
  675. W^.GetBounds(WI.Bounds);
  676. WI.Visible:=W^.GetState(sfVisible);
  677. WI.WinNb:=W^.Number;
  678. case WI.HelpCtx of
  679. hcSourceWindow :
  680. begin
  681. St:=SW^.Editor^.FileName; AddData(St,length(St)+1);
  682. L:=SW^.Editor^.GetFlags; AddData(L,sizeof(L));
  683. TP:=SW^.Editor^.SelStart; AddData(TP,sizeof(TP));
  684. TP:=SW^.Editor^.SelEnd; AddData(TP,sizeof(TP));
  685. TP:=SW^.Editor^.CurPos; AddData(TP,sizeof(TP));
  686. TP:=SW^.Editor^.Delta; AddData(TP,sizeof(TP));
  687. for L:=0 to 9 do begin
  688. BM:=SW^.Editor^.GetBookmark(L); AddData(BM,Sizeof(BM)); {save bookmarks}
  689. end;
  690. end;
  691. hcAsciiTableWindow :
  692. begin
  693. ch:=chr(PFPAsciiChart(P)^.Report^.AsciiChar);
  694. AddData(ch,sizeof(AnsiChar));
  695. end;
  696. end;
  697. WI.TitleLen:=length(Title);
  698. WI.ExtraDataSize:=XDataOfs;
  699. S^.Write(WI,sizeof(WI));
  700. S^.Write(Title[1],WI.TitleLen);
  701. if WI.ExtraDataSize>0 then
  702. S^.Write(XData,WI.ExtraDataSize);
  703. end;
  704. var W: word;
  705. OK: boolean;
  706. PV: PView;
  707. begin
  708. PushStatus(msg_storingdesktopcontents);
  709. New(S, Init(30*1024,4096));
  710. OK:=Assigned(S);
  711. if OK then
  712. begin
  713. W:=DesktopVersion;
  714. S^.Write(W,SizeOf(W));
  715. { S^.Put(Desktop);
  716. with Desktop^ do
  717. begin
  718. PutSubViewPtr(S^,CompilerMessageWindow);
  719. PutSubViewPtr(S^,CompilerStatusDialog);
  720. PutSubViewPtr(S^,ClipboardWindow);
  721. PutSubViewPtr(S^,CalcWindow);
  722. PutSubViewPtr(S^,GDBWindow);
  723. PutSubViewPtr(S^,BreakpointsWindow);
  724. PutSubViewPtr(S^,WatchesWindow);
  725. PutSubViewPtr(S^,UserScreenWindow);
  726. PutSubViewPtr(S^,ASCIIChart);
  727. PutSubViewPtr(S^,MessagesWindow);
  728. end;}
  729. { PV:=Application^.Last;
  730. while PV<>nil do
  731. begin
  732. CollectInfo(PV);
  733. PV:=PV^.PrevView;
  734. end;}
  735. PV:=Desktop^.Last;
  736. while PV<>nil do
  737. begin
  738. CollectInfo(PV);
  739. PV:=PV^.PrevView;
  740. end;
  741. OK:=(S^.Status=stOK);
  742. if OK then
  743. begin
  744. S^.Seek(0);
  745. OK:=F^.CreateResource(resDesktop,rcBinary,0);
  746. OK:=OK and F^.AddResourceEntryFromStream(resDesktop,langDefault,0,S^,S^.GetSize);
  747. end;
  748. Dispose(S, Done);
  749. end;
  750. if OK=false then
  751. ErrorBox(msg_errorstoringdesktop,nil);
  752. PopStatus;
  753. WriteOpenWindows:=OK;
  754. end;
  755. function WriteFlags(F: PResourceFile): boolean;
  756. var
  757. OK: boolean;
  758. begin
  759. F^.CreateResource(resDesktopFlags,rcBinary,0);
  760. OK:=F^.AddResourceEntry(resDesktopFlags,langDefault,0,DesktopFileFlags,
  761. SizeOf(DesktopFileFlags));
  762. if OK=false then
  763. ErrorBox(msg_errorwritingflags,nil);
  764. WriteFlags:=OK;
  765. end;
  766. function ReadCodeComplete(F: PResourceFile): boolean;
  767. var S: PMemoryStream;
  768. OK: boolean;
  769. begin
  770. PushStatus(msg_readingcodecompletewordlist);
  771. New(S, Init(1024,1024));
  772. OK:=F^.ReadResourceEntryToStream(resCodeComplete,langDefault,S^);
  773. S^.Seek(0);
  774. if OK then
  775. OK:=LoadCodeComplete(S^);
  776. Dispose(S, Done);
  777. if OK=false then
  778. ErrorBox(msg_errorloadingcodecompletewordlist,nil);
  779. PopStatus;
  780. ReadCodeComplete:=OK;
  781. end;
  782. function WriteCodeComplete(F: PResourceFile): boolean;
  783. var OK: boolean;
  784. S: PMemoryStream;
  785. begin
  786. PushStatus(msg_storingcodecompletewordlist);
  787. New(S, Init(1024,1024));
  788. OK:=StoreCodeComplete(S^);
  789. if OK then
  790. begin
  791. S^.Seek(0);
  792. F^.CreateResource(resCodeComplete,rcBinary,0);
  793. OK:=F^.AddResourceEntryFromStream(resCodeComplete,langDefault,0,S^,S^.GetSize);
  794. end;
  795. Dispose(S, Done);
  796. if OK=false then
  797. ErrorBox(msg_errorstoringcodecompletewordlist,nil);
  798. PopStatus;
  799. WriteCodeComplete:=OK;
  800. end;
  801. function ReadCodeTemplates(F: PResourceFile): boolean;
  802. var S: PMemoryStream;
  803. OK: boolean;
  804. begin
  805. PushStatus(msg_readingcodetemplates);
  806. New(S, Init(1024,4096));
  807. OK:=F^.ReadResourceEntryToStream(resCodeTemplates,langDefault,S^);
  808. S^.Seek(0);
  809. if OK then
  810. OK:=LoadCodeTemplates(S^);
  811. Dispose(S, Done);
  812. if OK=false then
  813. ErrorBox(msg_errorloadingcodetemplates,nil);
  814. PopStatus;
  815. ReadCodeTemplates:=OK;
  816. end;
  817. function WriteCodeTemplates(F: PResourceFile): boolean;
  818. var OK: boolean;
  819. S: PMemoryStream;
  820. begin
  821. PushStatus(msg_storingcodetemplates);
  822. New(S, Init(1024,4096));
  823. OK:=StoreCodeTemplates(S^);
  824. if OK then
  825. begin
  826. S^.Seek(0);
  827. F^.CreateResource(resCodeTemplates,rcBinary,0);
  828. OK:=F^.AddResourceEntryFromStream(resCodeTemplates,langDefault,0,S^,S^.GetSize);
  829. end;
  830. Dispose(S, Done);
  831. if OK=false then
  832. ErrorBox(msg_errorstoringcodetemplates,nil);
  833. PopStatus;
  834. WriteCodeTemplates:=OK;
  835. end;
  836. function ReadReturnToLastDir(F: PResourceFile): boolean;
  837. var S: PMemoryStream;
  838. OK: boolean;
  839. Dir:AnsiString;
  840. Size:sw_integer;
  841. begin
  842. PushStatus(msg_readingreturntolastdir);
  843. New(S, Init(1024,4096));
  844. OK:=F^.ReadResourceEntryToStream(ResLastDirectory,langDefault,S^);
  845. S^.Seek(0);
  846. if OK then
  847. begin
  848. S^.Read(Size, sizeof(Size)); { Read directory size }
  849. if Size>0 then
  850. begin
  851. Setlength(Dir,Size);
  852. S^.Read(Dir[1], Size); { Read the directory }
  853. {$i-}ChDir(Dir);{$i+}
  854. IOResult; {eat io result so it does not affect leater operations}
  855. GetDir(0,StartUpDir);
  856. end;
  857. end;
  858. Dispose(S, Done);
  859. if OK=false then
  860. ErrorBox(msg_errorloadingreturntolastdir,nil);
  861. PopStatus;
  862. ReadReturnToLastDir:=OK;
  863. end;
  864. function WriteReturnToLastDir(F: PResourceFile): boolean;
  865. var OK: boolean;
  866. S: PMemoryStream;
  867. Dir:AnsiString;
  868. Size:sw_integer;
  869. begin
  870. PushStatus(msg_storingreturntolastdir);
  871. New(S, Init(1024,4096));
  872. OK:=true;
  873. {$i-}GetDir(0,Dir);{$i+}
  874. if IOResult=0 then
  875. begin
  876. Size:=length(Dir);
  877. S^.Write(Size, sizeof(Size));
  878. if Size>0 then S^.Write(Dir[1],Size);
  879. S^.Seek(0);
  880. F^.CreateResource(ResLastDirectory,rcBinary,0);
  881. OK:=F^.AddResourceEntryFromStream(ResLastDirectory,langDefault,0,S^,S^.GetSize);
  882. end;
  883. Dispose(S, Done);
  884. if OK=false then
  885. ErrorBox(msg_errorstoringreturntolastdir,nil);
  886. PopStatus;
  887. WriteReturnToLastDir:=OK;
  888. end;
  889. function ReadFlags(F: PResourceFile): boolean;
  890. var
  891. OK: boolean;
  892. begin
  893. OK:=F^.ReadResourceEntry(resDesktopFlags,langDefault,DesktopFileFlags,
  894. sizeof(DesktopFileFlags));
  895. if OK=false then
  896. ErrorBox(msg_errorreadingflags,nil);
  897. ReadFlags:=OK;
  898. end;
  899. function WriteVideoMode(F: PResourceFile): boolean;
  900. var
  901. OK: boolean;
  902. begin
  903. F^.CreateResource(resVideo,rcBinary,0);
  904. OK:=F^.AddResourceEntry(resVideo,langDefault,0,ScreenMode,
  905. SizeOf(TVideoMode));
  906. if OK=false then
  907. ErrorBox(msg_errorstoringvideomode,nil);
  908. WriteVideoMode:=OK;
  909. end;
  910. function ReadVideoMode(F: PResourceFile;var NewScreenMode : TVideoMode): boolean;
  911. var
  912. OK,test : boolean;
  913. begin
  914. test:=F^.ReadResourceEntry(resVideo,langDefault,NewScreenMode,
  915. sizeof(NewScreenMode));
  916. if not test then
  917. NewScreenMode:=ScreenMode;
  918. OK:=test;
  919. if OK=false then
  920. ErrorBox(msg_errorreadingvideomode,nil);
  921. ReadVideoMode:=OK;
  922. end;
  923. function ReadSymbols(F: PResourceFile): boolean;
  924. var S: PMemoryStream;
  925. OK: boolean;
  926. R: PResource;
  927. begin
  928. ReadSymbols:=false; { if no symbols stored ... no problems }
  929. R:=F^.FindResource(resSymbols);
  930. if not Assigned(R) then
  931. exit;
  932. PushStatus(msg_readingsymbolinformation);
  933. New(S, Init(32*1024,4096));
  934. OK:=F^.ReadResourceEntryToStream(resSymbols,langDefault,S^);
  935. S^.Seek(0);
  936. if OK then
  937. OK:=LoadBrowserCol(S);
  938. Dispose(S, Done);
  939. if OK=false then
  940. ErrorBox(msg_errorloadingsymbolinformation,nil);
  941. PopStatus;
  942. ReadSymbols:=OK;
  943. end;
  944. function WriteSymbols(F: PResourceFile): boolean;
  945. var S: PMemoryStream;
  946. OK: boolean;
  947. begin
  948. OK:=Assigned(Modules);
  949. if OK then
  950. begin
  951. PushStatus(msg_storingsymbolinformation);
  952. New(S, Init(200*1024,4096));
  953. OK:=Assigned(S);
  954. if OK then
  955. OK:=StoreBrowserCol(S);
  956. if OK then
  957. begin
  958. S^.Seek(0);
  959. F^.CreateResource(resSymbols,rcBinary,0);
  960. OK:=F^.AddResourceEntryFromStream(resSymbols,langDefault,0,S^,S^.GetSize);
  961. end;
  962. Dispose(S, Done);
  963. if OK=false then
  964. ErrorBox(msg_errorstoringsymbolinformation,nil);
  965. PopStatus;
  966. end;
  967. WriteSymbols:=OK;
  968. end;
  969. function LoadDesktop: boolean;
  970. var OK,VOK: boolean;
  971. F: PResourceFile;
  972. VM : TVideoMode;
  973. begin
  974. PushStatus(msg_readingdesktopfile);
  975. New(F, LoadFile(DesktopPath));
  976. OK:=false;
  977. if Assigned(F) then
  978. begin
  979. OK:=ReadFlags(F);
  980. VOK:=ReadVideoMode(F,VM);
  981. if VOK and ((VM.Col<>ScreenMode.Col) or
  982. (VM.Row<>ScreenMode.Row) or (VM.Color<>ScreenMode.Color)) then
  983. begin
  984. if Assigned(Application) then
  985. Application^.SetScreenVideoMode(VM);
  986. end;
  987. if ((DesktopFileFlags and dfHistoryLists)<>0) then
  988. OK:=ReadHistory(F) and OK;
  989. if ((DesktopFileFlags and dfWatches)<>0) then
  990. OK:=ReadWatches(F) and OK;
  991. if ((DesktopFileFlags and dfBreakpoints)<>0) then
  992. OK:=ReadBreakpoints(F) and OK;
  993. if ((DesktopFileFlags and dfOpenWindows)<>0) then
  994. OK:=ReadOpenWindows(F) and OK;
  995. { no errors if no browser info available PM }
  996. if ((DesktopFileFlags and dfSymbolInformation)<>0) then
  997. OK:=ReadSymbols(F) and OK;
  998. if ((DesktopFileFlags and dfCodeCompleteWords)<>0) then
  999. OK:=ReadCodeComplete(F) and OK;
  1000. if ((DesktopFileFlags and dfCodeTemplates)<>0) then
  1001. OK:=ReadCodeTemplates(F) and OK;
  1002. if not OverrideLastDirOption then
  1003. if ((DesktopFileFlags and dfReturnToLastDir)<>0) then
  1004. StartupOptions:=StartupOptions or soReturnToLastDir
  1005. else
  1006. StartupOptions:=StartupOptions and( not soReturnToLastDir);
  1007. if ((StartupOptions and soReturnToLastDir)<>0) then
  1008. OK:=ReadReturnToLastDir(F) and OK;
  1009. {$ifdef Unix}
  1010. OK:=ReadKeys(F) and OK;
  1011. {$endif Unix}
  1012. Dispose(F, Done);
  1013. end;
  1014. PopStatus;
  1015. LoadDesktop:=OK;
  1016. end;
  1017. function SaveDesktop: boolean;
  1018. var OK: boolean;
  1019. F: PResourceFile;
  1020. TempPath: string;
  1021. begin
  1022. TempPath:=DirOf(DesktopPath)+DesktopTempName;
  1023. PushStatus(msg_writingdesktopfile);
  1024. New(F, CreateFile(TempPath));
  1025. if Assigned(Clipboard) then
  1026. if (DesktopFileFlags and dfClipboardContent)<>0 then
  1027. Clipboard^.SetFlags(Clipboard^.GetFlags or efStoreContent)
  1028. else
  1029. Clipboard^.SetFlags(Clipboard^.GetFlags and not efStoreContent);
  1030. OK:=false;
  1031. if Assigned(F) then
  1032. begin
  1033. OK:=WriteFlags(F);
  1034. OK:=OK and WriteVideoMode(F);
  1035. if ((DesktopFileFlags and dfHistoryLists)<>0) then
  1036. OK:=OK and WriteHistory(F);
  1037. if ((DesktopFileFlags and dfWatches)<>0) then
  1038. OK:=OK and WriteWatches(F);
  1039. if ((DesktopFileFlags and dfBreakpoints)<>0) then
  1040. OK:=OK and WriteBreakpoints(F);
  1041. if ((DesktopFileFlags and dfOpenWindows)<>0) then
  1042. OK:=OK and WriteOpenWindows(F);
  1043. { no errors if no browser info available PM }
  1044. if ((DesktopFileFlags and dfSymbolInformation)<>0) then
  1045. OK:=OK and (WriteSymbols(F) or not Assigned(Modules));
  1046. if ((DesktopFileFlags and dfCodeCompleteWords)<>0) then
  1047. OK:=OK and WriteCodeComplete(F);
  1048. if ((DesktopFileFlags and dfCodeTemplates)<>0) then
  1049. OK:=OK and WriteCodeTemplates(F);
  1050. {if ((DesktopFileFlags and dfReturnToLastDir)<>0) then
  1051. always write last dir }
  1052. OK:=WriteReturnToLastDir(F) and OK;
  1053. {$ifdef Unix}
  1054. OK:=OK and WriteKeys(F);
  1055. {$endif Unix}
  1056. Dispose(F, Done);
  1057. end;
  1058. if OK then
  1059. begin
  1060. if ExistsFile(DesktopPath) then
  1061. OK:=EraseFile(DesktopPath);
  1062. OK:=OK and RenameFile(TempPath,DesktopPath);
  1063. if OK=false then
  1064. ErrorBox(msg_failedtoreplacedesktopfile,nil);
  1065. end;
  1066. PopStatus;
  1067. SaveDesktop:=OK;
  1068. end;
  1069. function WriteSymbolsFile(const filename : string): boolean;
  1070. var OK: boolean;
  1071. F: PResourceFile;
  1072. begin
  1073. WriteSymbolsFile:=false;
  1074. If not assigned(Modules) then
  1075. exit;
  1076. New(F, CreateFile(FileName));
  1077. OK:=Assigned(F);
  1078. if OK and ((DesktopFileFlags and dfSymbolInformation)<>0) then
  1079. OK:=OK and WriteSymbols(F);
  1080. if assigned(F) then
  1081. Dispose(F,Done);
  1082. WriteSymbolsFile:=OK;
  1083. end;
  1084. function ReadSymbolsFile(const FileName : string): boolean;
  1085. var OK: boolean;
  1086. F: PResourceFile;
  1087. begin
  1088. ReadSymbolsFile:=false;
  1089. { Don't read again !! }
  1090. If assigned(Modules) then
  1091. exit;
  1092. New(F, LoadFile(FileName));
  1093. OK:=Assigned(F);
  1094. if OK and ((DesktopFileFlags and dfSymbolInformation)<>0) then
  1095. OK:=OK and ReadSymbols(F);
  1096. if assigned(F) then
  1097. Dispose(F,Done);
  1098. ReadSymbolsFile:=OK;
  1099. end;
  1100. END.