1 ; **************************************************************************** 2 ; pwd386.s (pwd3.s) - by Erdogan Tan - 05/05/2022 3 ; ---------------------------------------------------------------------------- 4 ; Retro UNIX 386 v1.2 - pwd - print working directory pathname 5 ; 6 ; [ Last Modification: 15/05/2022 ] 7 ; 8 ; Derived from (original) UNIX v5 (& v7) 'pwd.c' source Code 9 ; Ref: 10 ; www.tuhs.org (https://minnie.tuhs.org) 11 ; v5root.tar.gz 12 ; **************************************************************************** 13 ; [ usr/source/s2/pwd.c (archive date: 27-11-1974) ] 14 15 ; pwd0.s - Retro UNIX 8086 v1 (16 bit version of 'pwd1.s') 16 ; pwd1.s - Retro UNIX 386 v1 (unix v1 inode structure) 17 ; pwd2.s - Retro UNIX 386 v1.1 (16 byte directory entries) 18 ; pwd3.s - Retro UNIX 386 v1.2 (& v2) (modified unix v7 inode) 19 20 ; UNIX v1 system calls 21 _rele equ 0 22 _exit equ 1 23 _fork equ 2 24 _read equ 3 25 _write equ 4 26 _open equ 5 27 _close equ 6 28 _wait equ 7 29 _creat equ 8 30 _link equ 9 31 _unlink equ 10 32 _exec equ 11 33 _chdir equ 12 34 _time equ 13 35 _mkdir equ 14 36 _chmod equ 15 37 _chown equ 16 38 _break equ 17 39 _stat equ 18 40 _seek equ 19 41 _tell equ 20 42 _mount equ 21 43 _umount equ 22 44 _setuid equ 23 45 _getuid equ 24 46 _stime equ 25 47 _quit equ 26 48 _intr equ 27 49 _fstat equ 28 50 _emt equ 29 51 _mdate equ 30 52 _stty equ 31 53 _gtty equ 32 54 _ilgins equ 33 55 _sleep equ 34 ; Retro UNIX 8086 v1 feature only ! 56 _msg equ 35 ; Retro UNIX 386 v1 feature only ! 57 58 ;;; 59 ESCKey equ 1Bh 60 EnterKey equ 0Dh 61 62 %macro sys 1-4 63 ; 03/09/2015 64 ; 13/04/2015 65 ; Retro UNIX 386 v1 system call. 66 %if %0 >= 2 67 mov ebx, %2 68 %if %0 >= 3 69 mov ecx, %3 70 %if %0 = 4 71 mov edx, %4 72 %endif 73 %endif 74 %endif 75 mov eax, %1 76 int 30h 77 %endmacro 78 79 ; Retro UNIX 386 v1 system call format: 80 ; sys systemcall (eax) , , 81 82 [BITS 32] ; 32-bit intructions (for 80386 protected mode) 83 84 [ORG 0] 85 86 START_CODE: 87 ; 06/05/2022 88 ; 05/05/2022 89 90 ;main() { 91 ; int n; 92 93 ; clear (reset) stack (not necessary) 94 00000000 59 pop ecx ; ecx = number of arguments 95 pwd_0: 96 00000001 58 pop eax ; eax = argument 0 = executable file name 97 00000002 E2FD loop pwd_0 98 99 ;mov byte [y.zero], 0 ; (not necessary) 100 ; (because Retro UNIX kernel 101 ; clears bss -memory page- while 102 ; assigning it to program) 103 ;mov dword [off], 0 104 105 ; 06/05/2022 106 00000004 FF0D[3C040000] dec dword [off] ; -1 107 108 ;loop0: 109 ; stat(dot, &x); 110 ; if((file = open(dotdot,0)) < 0) prname(); 111 112 loop0: 113 ;sys _stat, dot, _x 114 115 ; 14/05/2022 116 ;stat(dot, &d); 117 ;if (d.st_ino==rino && d.st_dev==rdev) 118 ; prname(); 119 120 sys _stat, dot, _d 63 <1> 64 <1> 65 <1> 66 <1> %if %0 >= 2 67 0000000A BB[F6010000] <1> mov ebx, %2 68 <1> %if %0 >= 3 69 0000000F B9[42040000] <1> mov ecx, %3 70 <1> %if %0 = 4 71 <1> mov edx, %4 72 <1> %endif 73 <1> %endif 74 <1> %endif 75 00000014 B812000000 <1> mov eax, %1 76 00000019 CD30 <1> int 30h 121 0000001B 723D jc short error 122 123 0000001D 66833D[42040000]01 cmp word [d.ino], 1 ; d.st_ino == rino 124 ;cmp word [d.ino], 41 ; d.st_ino == rino 125 00000025 7504 jne short pwd_1 126 00000027 09C0 or eax, eax ; [d.dev] 127 ;or ax, ax ; [d.dev] ; && d.st_dev==rdev 128 ;jz short prname ; root device, root dir 129 00000029 742A jz short pwd_p ; 14/05/2022 130 pwd_1: 131 0000002B 66A3[40040000] mov [d.dev], ax 132 133 ; 15/05/2022 134 sys _open, dotdot, 0 ; open for read 63 <1> 64 <1> 65 <1> 66 <1> %if %0 >= 2 67 00000031 BB[F5010000] <1> mov ebx, %2 68 <1> %if %0 >= 3 69 00000036 B900000000 <1> mov ecx, %3 70 <1> %if %0 = 4 71 <1> mov edx, %4 72 <1> %endif 73 <1> %endif 74 <1> %endif 75 0000003B B805000000 <1> mov eax, %1 76 00000040 CD30 <1> int 30h 135 ;jc short prname 136 ; 14/05/2022 137 00000042 731D jnc short pwd_2 138 139 ; 14/05/2022 140 pwd_err: 141 00000044 B8[07020000] mov eax, err_1 142 pmsg_exit: 143 00000049 E88D010000 call print_msg 144 exit: 145 sys _exit ; exit(1); 63 <1> 64 <1> 65 <1> 66 <1> %if %0 >= 2 67 <1> mov ebx, %2 68 <1> %if %0 >= 3 69 <1> mov ecx, %3 70 <1> %if %0 = 4 71 <1> mov edx, %4 72 <1> %endif 73 <1> %endif 74 <1> %endif 75 0000004E B801000000 <1> mov eax, %1 76 00000053 CD30 <1> int 30h 146 ;hang: 147 ; nop 148 ; jmp short hang 149 150 151 pwd_p: ; 14/05/2022 152 00000055 E9E6000000 jmp prname 153 154 error: ; 14/05/2022 155 0000005A B8[FC010000] mov eax, err_0 156 0000005F EBE3 jmp short pwd_err 157 158 pwd_2: 159 160 ;loop1: 161 ; if((n = read(file,&y,16)) < 16) prname(); 162 ; if(y.jnum != x.inum)goto loop1; 163 ; close(file); 164 ; if(y.jnum == 1) ckroot(); 165 ; cat(); 166 ; chdir(dotdot); 167 ; goto loop0; 168 ;} 169 170 00000061 A3[38040000] mov [file], eax 171 172 ; 14/05/2022 173 ;fstat(file, &dd); 174 ;chdir(dotdot); 175 176 sys _fstat, eax, _dd 63 <1> 64 <1> 65 <1> 66 <1> %if %0 >= 2 67 00000066 89C3 <1> mov ebx, %2 68 <1> %if %0 >= 3 69 00000068 B9[84040000] <1> mov ecx, %3 70 <1> %if %0 = 4 71 <1> mov edx, %4 72 <1> %endif 73 <1> %endif 74 <1> %endif 75 0000006D B81C000000 <1> mov eax, %1 76 00000072 CD30 <1> int 30h 177 00000074 72E4 jc short error 178 179 ;mov [dd.dev], ax 180 00000076 89C1 mov ecx, eax 181 182 sys _chdir, dotdot 63 <1> 64 <1> 65 <1> 66 <1> %if %0 >= 2 67 00000078 BB[F5010000] <1> mov ebx, %2 68 <1> %if %0 >= 3 69 <1> mov ecx, %3 70 <1> %if %0 = 4 71 <1> mov edx, %4 72 <1> %endif 73 <1> %endif 74 <1> %endif 75 0000007D B80C000000 <1> mov eax, %1 76 00000082 CD30 <1> int 30h 183 00000084 72D4 jc short error 184 185 00000086 663B0D[40040000] cmp cx, [d.dev] 186 0000008D 7557 jne short pwd_4 187 188 0000008F 66A1[42040000] mov ax, [d.ino] 189 00000095 663B05[84040000] cmp ax, [dd.ino] 190 ;je short prname 191 ; 14/05/2022 192 0000009C 7505 jne short loop1 193 0000009E E99D000000 jmp prname 194 195 ; do .. while 196 loop1: 197 ;;sys _read, [file], _y, 10 ; Retro UNIX 386 v1 198 sys _read, [file], _y, 16 ; Retro UNIX 386 v1.1 & v1.2 63 <1> 64 <1> 65 <1> 66 <1> %if %0 >= 2 67 000000A3 8B1D[38040000] <1> mov ebx, %2 68 <1> %if %0 >= 3 69 000000A9 B9[C6040000] <1> mov ecx, %3 70 <1> %if %0 = 4 71 000000AE BA10000000 <1> mov edx, %4 72 <1> %endif 73 <1> %endif 74 <1> %endif 75 000000B3 B803000000 <1> mov eax, %1 76 000000B8 CD30 <1> int 30h 199 ;jc short prname 200 ; 14/05/2022 201 000000BA 7247 jc short pwd_5 202 ;cmp eax, 16 ; cmp eax, 10 203 ;;jb short prname 204 ;jb short pwd_5 ; 14/05/2022 205 000000BC 09C0 or eax, eax 206 ;jz short prname 207 000000BE 7443 jz short pwd_5 ; 14/05/2022 208 209 ; 14/05/2022 210 ; while (dir.d_ino != d.st_ino); 211 000000C0 66A1[C6040000] mov ax, [jnum] 212 ;cmp ax, [inum] 213 000000C6 663B05[42040000] cmp ax, [d.ino] 214 000000CD 75D4 jne short loop1 215 pwd_3: 216 sys _close, [file] 63 <1> 64 <1> 65 <1> 66 <1> %if %0 >= 2 67 000000CF 8B1D[38040000] <1> mov ebx, %2 68 <1> %if %0 >= 3 69 <1> mov ecx, %3 70 <1> %if %0 = 4 71 <1> mov edx, %4 72 <1> %endif 73 <1> %endif 74 <1> %endif 75 000000D5 B806000000 <1> mov eax, %1 76 000000DA CD30 <1> int 30h 217 218 ;cmp word [jnum], 1 ; Retro UNIX 386 v1.2 219 ;;cmp word [jnum], 41 ; root dir inode number 220 ;je short ckroot 221 ;call cat 222 ;sys _chdir, dotdot 223 ;jmp short loop0 224 225 ; 14/05/2022 226 000000DC E8A4000000 call cat 227 000000E1 E924FFFFFF jmp loop0 ; for (;;) 228 pwd_4: 229 loop_2: 230 ; 14/05/2022 231 ; else do .. while 232 ;sys _read, [file], _y, 10 ; Retro UNIX 386 v1 233 sys _read, [file], _y, 16 ; Retro UNIX 386 v1.1 & v1.2 63 <1> 64 <1> 65 <1> 66 <1> %if %0 >= 2 67 000000E6 8B1D[38040000] <1> mov ebx, %2 68 <1> %if %0 >= 3 69 000000EC B9[C6040000] <1> mov ecx, %3 70 <1> %if %0 = 4 71 000000F1 BA10000000 <1> mov edx, %4 72 <1> %endif 73 <1> %endif 74 <1> %endif 75 000000F6 B803000000 <1> mov eax, %1 76 000000FB CD30 <1> int 30h 234 000000FD 7204 jc short pwd_5 235 000000FF 21C0 and eax, eax 236 00000101 750A jnz short pwd_6 237 pwd_5: 238 00000103 B8[20020000] mov eax, err_2 239 00000108 E93CFFFFFF jmp pmsg_exit 240 pwd_6: 241 ; stat(dir.d_name, &dd); 242 sys _stat, yname, _dd 63 <1> 64 <1> 65 <1> 66 <1> %if %0 >= 2 67 0000010D BB[C8040000] <1> mov ebx, %2 68 <1> %if %0 >= 3 69 00000112 B9[84040000] <1> mov ecx, %3 70 <1> %if %0 = 4 71 <1> mov edx, %4 72 <1> %endif 73 <1> %endif 74 <1> %endif 75 00000117 B812000000 <1> mov eax, %1 76 0000011C CD30 <1> int 30h 243 0000011E 7305 jnc short pwd_7 244 00000120 E935FFFFFF jmp error 245 pwd_7: 246 ; while(dd.st_ino != d.st_ino || dd.st_dev != d.st_dev); 247 00000125 668B0D[42040000] mov cx, [d.ino] 248 0000012C 663B0D[84040000] cmp cx, [dd.ino] 249 00000133 75B1 jne short loop_2 250 00000135 663B05[40040000] cmp ax, [d.dev] 251 0000013C 75A8 jne short loop_2 252 0000013E EB8F jmp short pwd_3 253 254 ;prname() { 255 ; name[off] = '\n'; 256 ; write(1,name,off+1); 257 ; exit(); 258 259 prname: 260 sys _write, 1, nextline, 3 ; 06/05/2022 63 <1> 64 <1> 65 <1> 66 <1> %if %0 >= 2 67 00000140 BB01000000 <1> mov ebx, %2 68 <1> %if %0 >= 3 69 00000145 B9[F8010000] <1> mov ecx, %3 70 <1> %if %0 = 4 71 0000014A BA03000000 <1> mov edx, %4 72 <1> %endif 73 <1> %endif 74 <1> %endif 75 0000014F B804000000 <1> mov eax, %1 76 00000154 CD30 <1> int 30h 261 262 00000156 8B35[3C040000] mov esi, [off] 263 264 ; 14/05/2022 265 ;if (off<0) off = 0; 266 0000015C 46 inc esi ; -1 -> 0 267 0000015D 7401 jz short prname_crlf 268 0000015F 4E dec esi 269 prname_crlf: 270 ;mov byte [esi+name], 0Dh ; CR 271 00000160 66C786[38020000]0D- mov word [esi+name], 0A0Dh ; CRLF 271 00000168 0A 272 ;inc dword [off] 273 00000169 46 inc esi 274 0000016A 46 inc esi 275 ;mov [off], esi 276 ;sys _write, 1, name, [off] 277 sys _write, 1, name, esi 63 <1> 64 <1> 65 <1> 66 <1> %if %0 >= 2 67 0000016B BB01000000 <1> mov ebx, %2 68 <1> %if %0 >= 3 69 00000170 B9[38020000] <1> mov ecx, %3 70 <1> %if %0 = 4 71 00000175 89F2 <1> mov edx, %4 72 <1> %endif 73 <1> %endif 74 <1> %endif 75 00000177 B804000000 <1> mov eax, %1 76 0000017C CD30 <1> int 30h 278 _exit_: 279 sys _exit 63 <1> 64 <1> 65 <1> 66 <1> %if %0 >= 2 67 <1> mov ebx, %2 68 <1> %if %0 >= 3 69 <1> mov ecx, %3 70 <1> %if %0 = 4 71 <1> mov edx, %4 72 <1> %endif 73 <1> %endif 74 <1> %endif 75 0000017E B801000000 <1> mov eax, %1 76 00000183 CD30 <1> int 30h 280 ;hang: 281 ; nop 282 ; jmp short hang 283 284 ;ckroot() { 285 ; int i, n; 286 ; 287 ; if((n = stat(y.name,&x)) < 0) prname(); 288 ; i = x.devn; 289 ; if((n = chdir(root)) < 0) prname(); 290 ; if((file = open(root,0)) < 0) prname(); 291 ;loop: 292 ; if((n = read(file,&y,16)) < 16) prname(); 293 ; if(y.jnum == 0) goto loop; 294 ; if((n = stat(y.name,&x)) < 0) prname(); 295 ; if(x.devn != i) goto loop; 296 ; x.i[0] =& 060000; 297 ; if(x.i[0] != 040000) goto loop; 298 ; cat(); 299 ; prname(); 300 301 ; 14/05/2022 302 ; ; 06/05/2022 303 ; ; Note: For Retro UNIX 386 v1 & v1.1 & v1.2, 304 ; ; mounted device is handled via 'mnti' 305 ; ; field which keeps (device 0) mounting 306 ; ; directory inode number for mounted 307 ; ; device (1). Device number (0 or 1) check 308 ; ; (via 'sysstat') is not possible 309 ; ; for current Retro UNIX kernel versions 310 ; ; because 'sysstat' output does not contain 311 ; ; device number. 312 ; ; *** 313 ; ; As a temporary solution (before a next 314 ; ; kernel version with new 'sysstat'), 315 ; ; root dir entries are checked for a subdir 316 ; ; ('usr' & 'mnt' dirs for now) with root dir 317 ; ; inode number (41 or 1), if there is.. 318 ; ; root directory is a real (device 0) root 319 ; ; directory; if not, device 1 root directory 320 ; ; is mounted to a sub directory of device 0. 321 ; ; (Also it must be verified after 'chdir /') 322 ; ; 323 ; ; assumptions... 324 ; ; a sub dir with root inode number 325 ; ; dotdot / - chdir / 326 ; ; no - no ----> root 327 ; ; yes - (yes) --> root, not checked 328 ; ; no - yes ----> mounted 329 ; ; yes - (no) ---> root, not checked 330 ; 331 ;ckroot: 332 ; ; 06/05/2022 333 ; ; check 'usr' directory 334 ; mov edx, usr 335 ; call statm 336 ; jz short ckroot_2 ; root dir 337 ; ; check 'mnt' directory 338 ; mov edx, mnt 339 ; call statm 340 ; jz short ckroot_2 ; root dir 341 ; 342 ; sys _chdir, root 343 ; jc short ckroot_2 ; jmp short prname 344 ; 345 ; ; check 'usr' directory 346 ; mov edx, usr 347 ; call statm 348 ; jz short ckroot_1 ; mounted 349 ; ; check 'mnt' directory 350 ; mov edx, mnt 351 ; call statm 352 ; jnz short ckroot_2 ; not mounted 353 ; 354 ; ; mounted 355 ;ckroot_1: 356 ; ; move mounting directory name 357 ; mov esi, edx 358 ; mov edi, yname 359 ; movsd 360 ; ; concatenate (add to head of the path) 361 ; call cat 362 ;ckroot_2: 363 ; jmp prname 364 ; 365 ;statm: 366 ; ; 06/05/2022 367 ; sys _stat, edx, _x 368 ; jc short statm_1 369 ; cmp word [inum], 1 ; Retro UNIX 386 v1.2 370 ; ;cmp word [inum], 41 ; root dir inode number 371 ;statm_1: 372 ; retn 373 374 375 ;cat() { 376 ; int i, j; 377 ; 378 ; i = -1; 379 ; while(y.name[++i] != 0); 380 ; if((off+i+2) > 511) prname(); 381 ; for(j=off+1; j>=0; --j) name[j+i+1] = name[j]; 382 ; off=i+off+1; 383 ; name[i] = root[0]; 384 ; for(--i; i>=0; --i) name[i] = y.name[i]; 385 ;} 386 387 cat: 388 00000185 31DB xor ebx, ebx 389 00000187 4B dec ebx ; i = -1 390 cat_0: 391 00000188 43 inc ebx ; ++i 392 00000189 80BB[C8040000]00 cmp byte [yname+ebx], 0 393 00000190 77F6 ja short cat_0 394 00000192 89DA mov edx, ebx ; i 395 00000194 8B0D[3C040000] mov ecx, [off] 396 0000019A 41 inc ecx ; j = [off]+1 397 0000019B 01CA add edx, ecx ; edx = [off]+i+1 398 0000019D 81FAFD010000 cmp edx, 511-2 ; (+ CRLF + 0) 399 000001A3 779B ja short prname ; 14/05/2022 400 ;;ja short ckroot_2 ; jmp prname 401 ;ja short ckroot_err 402 000001A5 BE[38020000] mov esi, name 403 000001AA 01CE add esi, ecx ; name[j] 404 000001AC 89F7 mov edi, esi 405 000001AE 01DF add edi, ebx ; name[j+i] 406 000001B0 47 inc edi ; name[j+i+1] 407 cat_1: 408 ;std 409 ;rep stosb 410 ;cld 411 000001B1 49 dec ecx 412 000001B2 7808 js short cat_2 413 000001B4 4E dec esi 414 000001B5 8A06 mov al, [esi] 415 000001B7 4F dec edi 416 000001B8 8807 mov [edi], al 417 000001BA EBF5 jmp short cat_1 418 cat_2: 419 000001BC 8915[3C040000] mov [off], edx ; [off] = i+[off]+1 420 000001C2 C683[38020000]2F mov byte [name+ebx], '/' ; name[i] = root[0] 421 cat_3: 422 000001C9 4B dec ebx ; --i 423 000001CA 780E js short cat_4 ; 0 -> -1 424 ; name[i] = yname[i] 425 000001CC 8A83[C8040000] mov al, [yname+ebx] 426 000001D2 8883[38020000] mov [name+ebx], al 427 000001D8 EBEF jmp short cat_3 ; i >= 0 428 cat_4: 429 000001DA C3 retn 430 431 ;----------------------------------------------------------------- 432 433 print_msg: 434 ; 08/05/2022 435 ; eax = asciiz string address 436 000001DB 89C2 mov edx, eax 437 000001DD 4A dec edx 438 nextchr: 439 000001DE 42 inc edx 440 000001DF 803A00 cmp byte [edx], 0 441 000001E2 77FA ja short nextchr 442 ;cmp [edx], 0Dh 443 ;ja short nextchr 444 000001E4 29C2 sub edx, eax 445 ; edx = asciiz string length 446 ; 447 sys _write, 1, eax 63 <1> 64 <1> 65 <1> 66 <1> %if %0 >= 2 67 000001E6 BB01000000 <1> mov ebx, %2 68 <1> %if %0 >= 3 69 000001EB 89C1 <1> mov ecx, %3 70 <1> %if %0 = 4 71 <1> mov edx, %4 72 <1> %endif 73 <1> %endif 74 <1> %endif 75 000001ED B804000000 <1> mov eax, %1 76 000001F2 CD30 <1> int 30h 448 ; 449 000001F4 C3 retn 450 451 ;----------------------------------------------------------------- 452 ; data - initialized data 453 ;----------------------------------------------------------------- 454 455 ; 05/05/2022 456 457 000001F5 2E dotdot: db '.' 458 000001F6 2E dot: db '.' 459 000001F7 00 db 0 460 461 ; 06/05/2022 462 nextline: 463 000001F8 0D0A db 0Dh, 0Ah 464 000001FA 2F00 root: db '/', 0 465 466 ; 14/05/2022 467 ; default mounting directories (for current retro unix version) 468 ;usr: db 'usr', 0 469 ;mnt: db 'mnt', 0 470 471 ; 14/05/2022 472 000001FC 0D0A err_0: db 0Dh, 0Ah 473 000001FE 4572726F7221 db "Error!" 474 00000204 0D0A00 db 0dh, 0Ah, 0 475 476 00000207 0D0A err_1: db 0Dh, 0Ah 477 00000209 7077643A2063616E20- db "pwd: can not open .." 477 00000212 6E6F74206F70656E20- 477 0000021B 2E2E 478 0000021D 0D0A00 db 0Dh, 0Ah, 0 479 00000220 0D0A err_2: db 0Dh, 0Ah 480 00000222 72656164206572726F- db "read error in .." 480 0000022B 7220696E202E2E 481 00000232 0D0A00 db 0Dh, 0Ah, 0 482 483 ;----------------------------------------------------------------- 484 ; bss - uninitialized data 485 ;----------------------------------------------------------------- 486 487 00000235 90 align 4 488 489 bss_start: 490 491 ABSOLUTE bss_start 492 493 ; 05/05/2022 494 495 00000238 name: resb 512 496 497 00000438 ???????? file: resd 1 498 0000043C ???????? off: resd 1 499 500 ; 14/05/2022 501 idev: 502 00000440 ???? d.dev: resw 1 ; device number (0 = root, 1 = mounted) 503 ;dd.dev: resw 1 504 505 _x: ; stat(us) buffer 506 _d: ; 14/05/2022 507 inum: 508 d.ino: ; 14/05/2022 509 00000442 ???? resw 1 510 ximode: 511 d.mode: ; 14/05/22022 512 00000444 resb 64 ; Retro UNIX 386 v1.2 513 ;resb 32 ; Retro UNIX 386 v1 & v1.1 514 515 ; 14/05/2022 516 _dd: ; stat(us) buffer 517 00000484 ???? dd.ino: resw 1 518 dd.mode: 519 00000486 resb 64 ; Retro UNIX 386 v1.2 520 ;resb 32 ; Retro UNIX 386 v1 & v1.1 521 522 _y: ; directory entry buffer 523 000004C6 ???? jnum: resw 1 524 000004C8 yname: resb 14 ; Retro UNIX 386 v1.1 & v1.2 525 ;resb 8 ; Retro UNIX 386 v1 (unix v1) 526 000004D6 ???? yzero: resw 1 527 528 ;----------------------------------------------------------------- 529 ; Original UNIX v7 - /bin/pwd file - c source code (pwd.c) 530 ;----------------------------------------------------------------- 531 ; 532 ;/* 533 ; * Print working (current) directory 534 ; */ 535 ;#include 536 ;#include 537 ;#include 538 ;#include 539 ; 540 ;char dot[] = "."; 541 ;char dotdot[] = ".."; 542 ;char name[512]; 543 ;int file; 544 ;int off = -1; 545 ;struct stat d, dd; 546 ;struct direct dir; 547 ; 548 ;main() 549 ;{ 550 ; int rdev, rino; 551 ; 552 ; stat("/", &d); 553 ; rdev = d.st_dev; 554 ; rino = d.st_ino; 555 ; for (;;) { 556 ; stat(dot, &d); 557 ; if (d.st_ino==rino && d.st_dev==rdev) 558 ; prname(); 559 ; if ((file = open(dotdot,0)) < 0) { 560 ; fprintf(stderr,"pwd: cannot open ..\n"); 561 ; exit(1); 562 ; } 563 ; fstat(file, &dd); 564 ; chdir(dotdot); 565 ; if(d.st_dev == dd.st_dev) { 566 ; if(d.st_ino == dd.st_ino) 567 ; prname(); 568 ; do 569 ; if (read(file, (char *)&dir, sizeof(dir)) < sizeof(dir)) { 570 ; fprintf(stderr,"read error in ..\n"); 571 ; exit(1); 572 ; } 573 ; while (dir.d_ino != d.st_ino); 574 ; } 575 ; else do { 576 ; if(read(file, (char *)&dir, sizeof(dir)) < sizeof(dir)) { 577 ; fprintf(stderr,"read error in ..\n"); 578 ; exit(1); 579 ; } 580 ; stat(dir.d_name, &dd); 581 ; } while(dd.st_ino != d.st_ino || dd.st_dev != d.st_dev); 582 ; close(file); 583 ; cat(); 584 ; } 585 ;} 586 ; 587 ;prname() 588 ;{ 589 ; write(1, "/", 1); 590 ; if (off<0) 591 ; off = 0; 592 ; name[off] = '\n'; 593 ; write(1, name, off+1); 594 ; exit(0); 595 ;} 596 ; 597 ;cat() 598 ;{ 599 ; register i, j; 600 ; 601 ; i = -1; 602 ; while (dir.d_name[++i] != 0); 603 ; if ((off+i+2) > 511) 604 ; prname(); 605 ; for(j=off+1; j>=0; --j) 606 ; name[j+i+1] = name[j]; 607 ; off=i+off+1; 608 ; name[i] = '/'; 609 ; for(--i; i>=0; --i) 610 ; name[i] = dir.d_name[i]; 611 ;} 612 613 ; 05/05/2022 614 615 ;----------------------------------------------------------------- 616 ; Original UNIX v5 - /usr/bin/pwd file - c source code (pwd.c) 617 ;----------------------------------------------------------------- 618 ; 619 ;char dot[] "."; 620 ;char dotdot[] ".."; 621 ;char root[] "/"; 622 ;char name[512]; 623 ;int file, off -1; 624 ;struct statb {int devn, inum, i[18];}x; 625 ;struct entry { int jnum; char name[16];}y; 626 ; 627 ;main() { 628 ; int n; 629 ; 630 ;loop0: 631 ; stat(dot, &x); 632 ; if((file = open(dotdot,0)) < 0) prname(); 633 ;loop1: 634 ; if((n = read(file,&y,16)) < 16) prname(); 635 ; if(y.jnum != x.inum)goto loop1; 636 ; close(file); 637 ; if(y.jnum == 1) ckroot(); 638 ; cat(); 639 ; chdir(dotdot); 640 ; goto loop0; 641 ;} 642 ;ckroot() { 643 ; int i, n; 644 ; 645 ; if((n = stat(y.name,&x)) < 0) prname(); 646 ; i = x.devn; 647 ; if((n = chdir(root)) < 0) prname(); 648 ; if((file = open(root,0)) < 0) prname(); 649 ;loop: 650 ; if((n = read(file,&y,16)) < 16) prname(); 651 ; if(y.jnum == 0) goto loop; 652 ; if((n = stat(y.name,&x)) < 0) prname(); 653 ; if(x.devn != i) goto loop; 654 ; x.i[0] =& 060000; 655 ; if(x.i[0] != 040000) goto loop; 656 ; cat(); 657 ; prname(); 658 ;} 659 ;prname() { 660 ; name[off] = '\n'; 661 ; write(1,name,off+1); 662 ; exit(); 663 ;} 664 ;cat() { 665 ; int i, j; 666 ; 667 ; i = -1; 668 ; while(y.name[++i] != 0); 669 ; if((off+i+2) > 511) prname(); 670 ; for(j=off+1; j>=0; --j) name[j+i+1] = name[j]; 671 ; off=i+off+1; 672 ; name[i] = root[0]; 673 ; for(--i; i>=0; --i) name[i] = y.name[i]; 674 ;}