Sign in Join
Wiki copytemporary

Rosetta Stone: what changed

Revision 2 to 3. Removed lines have a minus sign; added lines have a plus sign.

OldNewLine
11## Introduction
22
33Often, people new to a programming language/library have trouble mapping the things they know how to do in other environments to the new environments.
44
55It can be handy to have a sort of "Rosetta stone" that roughly translates tasks from one environment/language into another.
66
77## Programming languages
88
99If you have experience in other programming languages (such as C++, Visual Basic), there are some Rosetta stone web pages that might help you. As the Free Pascal/Lazarus syntax and library is fairly consistent with Delphi's, sites that "translate" to Delphi are also a valuable resource.
1010
1111Some useful pages:
1212
1313- [<http://mc-computing.com/Languages/>](http://mc-computing.com/Languages/) This page has some explanation of the concepts involved
1414- [<http://rosettacode.org/wiki/Category:Pascal>](http://rosettacode.org/wiki/Category:Pascal) A huge number of languages, even esoteric, and tasks, make this site special
1515- [[Pascal for C users]]
1616- [[Pascal for CSharp users]]
1717- [[Pascal for Java users]]
1818
1919## Operating systems
2020
2121If you know how to do something in an operating system, chances are you can do the same using FPC/Lazarus.
2222
2323The table below gives a rough mapping of some tasks:
2424
2525**Windows/DOS**
2626
2727**Unix/Linux**
2828
2929**Description**
3030
3131**FreePascal/Lazarus**
3232
3333assoc
3434
3535Show/edit file associations
3636
3737See [[FileAssociation]]
3838
3939copy
4040
4141cp
4242
4343Copy file
4444
4545Lazarus [[CopyFile|fileutil.copyfile]]; roll your own with filestreams, see e.g. [[File Handling In Pascal|File_Handling_In_Pascal#FileCopy]]
4646
4747date /t
4848
4949date
5050
5151Show current date
5252
5353sysutils.now (date/time); sysutils.date (date); sysutils.time (time)
5454
5555del, erase
5656
5757rm, rm -f
5858
5959Delete file
6060
6161sysutils.deletefile, erase
6262
6363deltree, rmdir /s
6464
6565rm -r,rm -rf
6666
6767Remove directories with subdirectories
6868
6969Lazarus fileutil.deletedirectory
7070
7171dir
7272
7373ls
7474
7575Find files in a directory
7676
7777Lazarus [[FindAllFiles]]
7878
7979diskpart list volume
8080
8181mount
8282
8383Show partitions/volumes/drives on a computer
8484
8585Windows: see [[Windows Programming Tips|Windows_Programming_Tips#Listing_all_available_drives]]
8686
8787Linux: see [[Linux Programming Tips|Linux_Programming_Tips#Get_the_list_of_mounted_partitions]]
8888
8989Unix: you'll have to parse some files (e.g. /etc/mtab) yourself, depending on Unix flavour; see [Forum post](http://lazarus.freepascal.org/index.php/topic,15943.msg86569.html#msg86569)
9090
9191find
9292
9393grep
9494
9595Search for a text/string
9696
9797Several options, including the pos, ansipos functions. Regular expression support is provided by the [[RegEx packages]].
9898
9999ldifde
100100
101101ldapsearch
102102
103103Search through Active Directory/LDAP
104104
105105Use [[Synapse]] ldapsend unit to work with LDAP queries; see e.g. [example code on Leonardo Ramé's blog](http://leonardorame.blogspot.com/2007_02_01_archive.html)
106106
107107md5sum
108108
109109md5sum
110110
111111Calculate hash of file contents
112112
113113You can use the MDFile function in the md5 FPC unit.
114114
115115mkdir
116116
117117mkdir
118118
119119Create directory
120120
121121mkdir; forcedirectories (creates entire path, if necessary)
122122
123123move
124124
125125mv
126126
127127Move file to another directory
128128
129129Within partition/disk: sysutils.renamefile; otherwise copy and delete original
130130
131131rename, ren
132132
133133mv
134134
135135Rename file
136136
137137sysutils.renamefile (can also "move" a file between directories, but only on same partition/disk
138138
139139sc query \<servicename\>
140140
141141service --status-all
142142
143143Show status for service
144144
145145See [[ServiceManager]]
146146
147147?
148148
149149sed -i 's\|Delphi\|FreePascal\|g' readme.txt
150150
151151Search and replace text in file.
152152
153153See example code below.
154154
155155shutdown
156156
157157shutdown
158158
159159Shut down computer
160160
161161Windows: see [forum post](http://forum.lazarus.freepascal.org/index.php/topic,16258.msg87992.html#msg87992)
162162
163163tasklist
164164
165165ps
166166
167167List or find processes
168168
169169Windows: [[Windows Programming Tips|Windows_Programming_Tips#Showing.2Ffinding_processes]]
170170
171171?
172172
173173touch
174174
175175Create a new empty file
176176
177177sysutils.filecreate(filename)
178178
179179?
180180
181181touch
182182
183183Modify file time
184184
185185See [[Create a new file date/de]]
186186
187187?
188188
189189uname
190190
191191Get kernel/system info
192192
193193See uname function below.
194194
195195wget, curl
196196
197197wget, curl
198198
199199Download file from HTTP/FTP
200200
201201Multiple options, e.g. use synapse httpsend or ftpsend units: [[Synapse|Synapse#Downloading_files]]
202202
203203?
204204
205205which
206206
207207Search for executable in path
208208
209209Lazarus fileutil.FindDefaultExecutablePath; see also the example below.
210210
211211?
212212
213213whoami
214214
215215Find out username
216216
217217See UserName function below. On Windows: you can check if you're Administrator: winutils.iswindowsadmin(). On *nix: fpgeteuid shows you the effective userid (0 for root).
218218
219219## Emulating uname
220220
221221Works on Linux, probably FreeBSD:
222222
223223``` pascal
224224program uname;
225225
226226uses baseunix;
227227
228228var KernelName: UtsName;
229229
230230begin
231231 fpuname(KernelName);
232232 writeln(kernelname.sysname);
233233 writeln(kernelname.nodename);
234234 writeln(kernelname.release);
235235 writeln(kernelname.version);
236236 writeln(kernelname.machine);
237237 writeln(kernelname.domain);
238238end.
239239```
240240
241241Sample output:
242242
243-`Linux`\
244-`mydebianmachine`\
245-`3.12-1-amd64`\
246-`#1 SMP Debian 3.12.6-2 (2013-12-29)`\
247-`x86_64`\
248-`(none)`
243+```text
244+Linux
245+mydebianmachine
246+3.12-1-amd64
247+#1 SMP Debian 3.12.6-2 (2013-12-29)
248+x86_64
249+(none)
250+```
249251
250252## Emulating which
251253
252254Although Lazarus has FindDefaultExecutablePath, it has some flaws. Use e.g. this code:
253255
254256``` pascal
255257function Which(Executable: string): string;
256258var
257259 Output: string;
258260begin
259261 {$IFDEF UNIX}
260262 // Note: we're using external which because
261263 // FindDefaultExecutablePath
262264 // doesn't check if the user has execute permission
263265 // on the found file.
264266 ExecuteCommand('which '+Executable,Output,false);
265267 // Remove trailing LF(s) and other control codes:
266268 while (length(output)>0) and (ord(output[length(output)])<$20) do
267269 delete(output,length(output),1);
268270 {$ELSE}
269271 Output:=FindDefaultExecutablePath(Executable);
270272 {$ENDIF UNIX}
271273 // Extra check:
272274 if (Output<>'') and fileexists(Output) then
273275 begin
274276 result:=Output;
275277 end
276278 else
277279 begin
278280 result:=''; //command failed
279281 end;
280282end;
281283```
282284
283285## Emulating whoami
284286
285287... or getting the current user's operating system username. Returns a UTF8 string.
286288
287289``` pascal
288290uses
289291 {$IFDEF UNIX}
290292 {$IF (DEFINED(LINUX)) OR (DEFINED(FREEBSD))}
291293 ,users //not available on OSX
292294 {$ENDIF}
293295 ,baseunix //for fpgetuid
294296 .... //other unix stuff
295297 {$ENDIF}
296298 {$IFDEF MSWINDOWS}
297299 ,windows
298300 {$ENDIF}
299301 ,lazutf8
300302
301303function UserName: string;
302304// Get Operating System user name
303305{$IFDEF WINDOWS}
304306const
305307 MaxLen = 256;
306308var
307309 Len: DWORD;
308310 WS: WideString;
309311 Res: windows.BOOL;
310312{$ENDIF}
311313begin
312314 Result := '';
313315 {$IFDEF WINDOWS}
314316 Len := MaxLen;
315317 {$IFNDEF WINCE}
316318 // Check for Win98..WinME:
317319 if Win32MajorVersion <= 4 then
318320 begin
319321 SetLength(Result,MaxLen);
320322 Res := Windows.GetUserName(@Result[1], Len);
321323 if Res then
322324 begin
323325 SetLength(Result,Len-1);
324326 Result := SysToUtf8(Result);
325327 end
326328 else
327329 SetLength(Result,0);
328330 end
329331 else
330332 {$ENDIF NOT WINCE}
331333 begin
332334 SetLength(WS, MaxLen-1);
333335 Res := Windows.GetUserNameW(@WS[1], Len);
334336 if Res then
335337 begin
336338 SetLength(WS, Len - 1);
337339 Result := Utf16ToUtf8(WS);
338340 end
339341 else
340342 SetLength(Result,0);
341343 end;
342344 {$ENDIF WINDOWS}
343345 {$IFDEF UNIX}
344346 {$IF (DEFINED(LINUX)) OR (DEFINED(FREEBSD))}
345347 Result := SysToUtf8(GetUserName(fpgetuid));
346348 {$ENDIF}
347349 if Result = '' then
348350 Result := GetEnvironmentVariableUTF8('USER'); //fallback or other unixes which export $USER and don't support GetUserName
349351 {$ENDIF}
350352end;
351353```
352354
353355## Finding all occurrences of some bytes in a file
354356
355357A sort of grep. From forum post by KpjComp: [1](http://lazarus.freepascal.org/index.php/topic,16574.msg90287.html#msg90287)
356358
357359The block search class:
358360
359361``` pascal
360362unit block_search;
361363
362364{$mode objfpc}{$H+}
363365
364366interface
365367
366368uses
367369 Classes, SysUtils, fgl;
368370
369371type
370372
371373 { TBlockSearch }
372374 TBlockSearchResults = specialize TFPGList<int64>;
373375
374376 TBlockSearch = class
375377 private
376378 src:TStream;
377379 fresults:TBlockSearchResults;
378380 block:array of byte;
379381 public
380382 procedure SearchFor(a:array of byte);
381383 constructor Create(_Src:TStream; blocksize:integer = 1024*1024);
382384 destructor Destroy; override;
383385 property Results:TBlockSearchResults read fResults;
384386 end;
385387
386388implementation
387389
388390{ TBlockSearch }
389391
390392procedure TBlockSearch.SearchFor(a: array of byte);
391393var
392394 readsize:integer;
393395 fPos:Int64;
394396 fifoBuff:array of byte;
395397 fifoSt,fifoEn,searchLen,lpbyte:integer;
396398
397399 //
398400 procedure CheckPos;
399401 var
400402 l,p:integer;
401403 begin
402404 p := fifoST;
403405 for l := 0 to pred(SearchLen) do
404406 begin
405407 if a[l] <> fifoBuff[p] then exit;
406408 //p := (p+1) mod SearchLen, the if seems quicker
407409 inc(p); if p >= SearchLen then p := 0;
408410 end;
409411 fresults.Add(fpos-searchLen);
410412 end;
411413 //
412414begin
413415 fresults.clear;
414416 src.Position:=0;
415417 readsize := src.Read(block[0],Length(block));
416418 searchLen := length(a);
417419 if searchLen > length(block) then
418420 raise Exception.Create('Search term larger than blocksize');
419421 if readsize < searchLen then exit;
420422 setlength(fifoBuff,searchLen);
421423 move(block[0],fifoBuff[0],searchLen);
422424 fPos:=0;
423425 fifoSt:=0;
424426 fifoEn:=SearchLen-1;
425427 CheckPos;
426428 while readsize > 0 do
427429 begin
428430 for lpByte := 0 to pred(readsize) do
429431 begin
430432 inc(fifoSt); if fifoSt>=SearchLen then fifoST := 0;
431433 inc(fifoEn); if fifoEn>=SearchLen then fifoEn := 0;
432434 fifoBuff[fifoEn] := block[lpByte];
433435 inc(fPos);
434436 CheckPos;
435437 end;
436438 readsize := src.Read(block[0],Length(block));
437439 end;
438440end;
439441
440442constructor TBlockSearch.Create(_Src: TStream; blocksize: integer);
441443begin
442444 inherited Create;
443445 setlength(block,blocksize);
444446 src := _src;
445447 fresults := TBlockSearchResults.Create;
446448end;
447449
448450destructor TBlockSearch.Destroy;
449451begin
450452 freeAndNil(fresults);
451453 inherited Destroy;
452454end;
453455
454456end.
455457```
456458
457459Example of usage:
458460
459461``` pascal
460462var
461463 bs:TBlockSearch;
462464..
463465..
464466 bs := TBlockSearch.Create(SourceFile);
465467 try
466468 bs.SearchFor(WhatIAmSearchingFor);
467469 for i := 0 to bs.results.count-1 do
468470 begin
469471 // Example: we need to do something at an offset after the result
470472 SourceFile.Position := bs.Results.Items[i] + 5;
471473 SourceFile.ReadBuffer(RecordToParse, SizeOf(RecordToParse));
472474 // And now I work on the data in the second packed record of arrays and output to memo or whatever
473475 end;
474476 finally
475477 bs.free;
476478 end;
477479```
478480
479481## Search and replace in a file
480482
481483This will search and replace by loading the entire file into the stringlist in memory and replacing there, then saving the stringlist again. While fine for small files, performance will likely suffer for large files.
482484
483485``` pascal
484486procedure FindAndReplace(SearchFor, ReplaceWith, FileName: string);
485487var
486488 FileContents: TStringList;
487489begin
488490 FileContents:=TStringList.Create;
489491 try
490492 FileContents.LoadFromFile(FileName);
491493 FileContents.Text:=StringReplace(FileContents.Text, SearchFor, ReplaceWith, [rfReplaceAll,rfIgnoreCase]);
492494 FileContents.SaveToFile(FileName);
493495 finally
494496 FileContents.Free;
495497 end;
496498end;
497499```
498500
499501---
500502*From the Free Pascal wiki, page "Rosetta Stone", as it stood on 2021-11-23 after a change by Trev, out of the wiki's dump of 2024-05-26. Copyright stays with the author who wrote it, according to the old wiki's [[Licensing]] page. If you have concerns about this material, [message the admin](/wiki-contact).*
501503Category: Code
502504Category: Code Snippets
503505Category: FPC
504506Category: Lazarus
505507Category: Rosetta Stone
506508Category: Tutorials

Back to history