1 ; **************************************************************************** 2 ; pwd386.s (pwd2.s) - by Erdogan Tan - 05/05/2022 3 ; ---------------------------------------------------------------------------- 4 ; Retro UNIX 386 v1.1 - 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]29 cmp word [d.ino], 41 ; d.st_ino == rino 124 00000025 7504 jne short pwd_1 125 00000027 09C0 or eax, eax 126 ;or ax, ax ; [d.dev] ; && d.st_dev==rdev 127 ;jz short prname ; root device, root dir 128 00000029 742A jz short pwd_p ; 14/05/2022 129 pwd_1: 130 0000002B 66A3[40040000] mov [d.dev], ax 131 132 ; 15/05/2022 133 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 134 ;jc short prname 135 ; 14/05/2022 136 00000042 731D jnc short pwd_2 137 138 ; 14/05/2022 139 pwd_err: 140 00000044 B8[07020000] mov eax, err_1 141 pmsg_exit: 142 00000049 E88D010000 call print_msg 143 exit: 144 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 145 ;hang: 146 ; nop 147 ; jmp short hang 148 149 150 pwd_p: ; 14/05/2022 151 00000055 E9E6000000 jmp prname 152 153 error: ; 14/05/2022 154 0000005A B8[FC010000] mov eax, err_0 155 0000005F EBE3 jmp short pwd_err 156 157 pwd_2: 158 159 ;loop1: 160 ; if((n = read(file,&y,16)) < 16) prname(); 161 ; if(y.jnum != x.inum)goto loop1; 162 ; close(file); 163 ; if(y.jnum == 1) ckroot(); 164 ; cat(); 165 ; chdir(dotdot); 166 ; goto loop0; 167 ;} 168 169 00000061 A3[38040000] mov [file], eax 170 171 ; 14/05/2022 172 ;fstat(file, &dd); 173 ;chdir(dotdot); 174 175 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[64040000] <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 176 00000074 72E4 jc short error 177 178 ;mov [dd.dev], ax 179 00000076 89C1 mov ecx, eax 180 181 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 182 00000084 72D4 jc short error 183 184 00000086 663B0D[40040000] cmp cx, [d.dev] 185 0000008D 7557 jne short pwd_4 186 187 0000008F 66A1[42040000] mov ax, [d.ino] 188 00000095 663B05[64040000] cmp ax, [dd.ino] 189 ;je short prname 190 ; 14/05/2022 191 0000009C 7505 jne short loop1 192 0000009E E99D000000 jmp prname 193 194 ; do .. while 195 loop1: 196 ;;sys _read, [file], _y, 10 ; Retro UNIX 386 v1 197 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[86040000] <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 198 ;jc short prname 199 ; 14/05/2022 200 000000BA 7247 jc short pwd_5 201 ;cmp eax, 16 ; cmp eax, 10 202 ;;jb short prname 203 ;jb short pwd_5 ; 14/05/2022 204 000000BC 09C0 or eax, eax 205 ;jz short prname 206 000000BE 7443 jz short pwd_5 ; 14/05/2022 207 208 ; 14/05/2022 209 ; while (dir.d_ino != d.st_ino); 210 000000C0 66A1[86040000] mov ax, [jnum] 211 ;cmp ax, [inum] 212 000000C6 663B05[42040000] cmp ax, [d.ino] 213 000000CD 75D4 jne short loop1 214 pwd_3: 215 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 216 217 ;;cmp word [jnum], 1 ; Retro UNIX 386 v1.2 218 ;cmp word [jnum], 41 ; root dir inode number 219 ;je short ckroot 220 ;call cat 221 ;sys _chdir, dotdot 222 ;jmp short loop0 223 224 ; 11/05/2022 225 000000DC E8A4000000 call cat 226 000000E1 E924FFFFFF jmp loop0 ; for (;;) 227 pwd_4: 228 loop_2: 229 ; 14/05/2022 230 ; else do .. while 231 ;sys _read, [file], _y, 10 ; Retro UNIX 386 v1 232 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[86040000] <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 233 000000FD 7204 jc short pwd_5 234 000000FF 21C0 and eax, eax 235 00000101 750A jnz short pwd_6 236 pwd_5: 237 00000103 B8[20020000] mov eax, err_2 238 00000108 E93CFFFFFF jmp pmsg_exit 239 pwd_6: 240 ; stat(dir.d_name, &dd); 241 sys _stat, yname, _dd 63 <1> 64 <1> 65 <1> 66 <1> %if %0 >= 2 67 0000010D BB[88040000] <1> mov ebx, %2 68 <1> %if %0 >= 3 69 00000112 B9[64040000] <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 242 0000011E 7305 jnc short pwd_7 243 00000120 E935FFFFFF jmp error 244 pwd_7: 245 ; while(dd.st_ino != d.st_ino || dd.st_dev != d.st_dev); 246 00000125 668B0D[42040000] mov cx, [d.ino] 247 0000012C 663B0D[64040000] cmp cx, [dd.ino] 248 00000133 75B1 jne short loop_2 249 00000135 663B05[40040000] cmp ax, [d.dev] 250 0000013C 75A8 jne short loop_2 251 0000013E EB8F jmp short pwd_3 252 253 ;prname() { 254 ; name[off] = '\n'; 255 ; write(1,name,off+1); 256 ; exit(); 257 258 prname: 259 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 260 261 00000156 8B35[3C040000] mov esi, [off] 262 263 ; 14/05/2022 264 ;if (off<0) off = 0; 265 0000015C 46 inc esi ; -1 -> 0 266 0000015D 7401 jz short prname_crlf 267 0000015F 4E dec esi 268 prname_crlf: 269 ;mov byte [esi+name], 0Dh ; CR 270 00000160 66C786[38020000]0D- mov word [esi+name], 0A0Dh ; CRLF 270 00000168 0A 271 ;inc dword [off] 272 00000169 46 inc esi 273 0000016A 46 inc esi 274 ;mov [off], esi 275 ;sys _write, 1, name, [off] 276 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 277 _exit_: 278 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 279 ;hang: 280 ; nop 281 ; jmp short hang 282 283 ;ckroot() { 284 ; int i, n; 285 ; 286 ; if((n = stat(y.name,&x)) < 0) prname(); 287 ; i = x.devn; 288 ; if((n = chdir(root)) < 0) prname(); 289 ; if((file = open(root,0)) < 0) prname(); 290 ;loop: 291 ; if((n = read(file,&y,16)) < 16) prname(); 292 ; if(y.jnum == 0) goto loop; 293 ; if((n = stat(y.name,&x)) < 0) prname(); 294 ; if(x.devn != i) goto loop; 295 ; x.i[0] =& 060000; 296 ; if(x.i[0] != 040000) goto loop; 297 ; cat(); 298 ; prname(); 299 300 ; 14/05/2022 301 ; ; 06/05/2022 302 ; ; Note: For Retro UNIX 386 v1 & v1.1 & v1.2, 303 ; ; mounted device is handled via 'mnti' 304 ; ; field which keeps (device 0) mounting 305 ; ; directory inode number for mounted 306 ; ; device (1). Device number (0 or 1) check 307 ; ; (via 'sysstat') is not possible 308 ; ; for current Retro UNIX kernel versions 309 ; ; because 'sysstat' output does not contain 310 ; ; device number. 311 ; ; *** 312 ; ; As a temporary solution (before a next 313 ; ; kernel version with new 'sysstat'), 314 ; ; root dir entries are checked for a subdir 315 ; ; ('usr' & 'mnt' dirs for now) with root dir 316 ; ; inode number (41 or 1), if there is.. 317 ; ; root directory is a real (device 0) root 318 ; ; directory; if not, device 1 root directory 319 ; ; is mounted to a sub directory of device 0. 320 ; ; (Also it must be verified after 'chdir /') 321 ; ; 322 ; ; assumptions... 323 ; ; a sub dir with root inode number 324 ; ; dotdot / - chdir / 325 ; ; no - no ----> root 326 ; ; yes - (yes) --> root, not checked 327 ; ; no - yes ----> mounted 328 ; ; yes - (no) ---> root, not checked 329 ; 330 ;ckroot: 331 ; ; 06/05/2022 332 ; ; check 'usr' directory 333 ; mov edx, usr 334 ; call statm 335 ; jz short ckroot_2 ; root dir 336 ; ; check 'mnt' directory 337 ; mov edx, mnt 338 ; call statm 339 ; jz short ckroot_2 ; root dir 340 ; 341 ; sys _chdir, root 342 ; jc short ckroot_2 ; jmp short prname 343 ; 344 ; ; check 'usr' directory 345 ; mov edx, usr 346 ; call statm 347 ; jz short ckroot_1 ; mounted 348 ; ; check 'mnt' directory 349 ; mov edx, mnt 350 ; call statm 351 ; jnz short ckroot_2 ; not mounted 352 ; 353 ; ; mounted 354 ;ckroot_1: 355 ; ; move mounting directory name 356 ; mov esi, edx 357 ; mov edi, yname 358 ; movsd 359 ; ; concatenate (add to head of the path) 360 ; call cat 361 ;ckroot_2: 362 ; jmp prname 363 ; 364 ;statm: 365 ; ; 06/05/2022 366 ; sys _stat, edx, _x 367 ; jc short statm_1 368 ; ;cmp word [inum], 1 ; Retro UNIX 386 v1.2 369 ; cmp word [inum], 41 ; root dir inode number 370 ;statm_1: 371 ; retn 372 373 ;cat() { 374 ; int i, j; 375 ; 376 ; i = -1; 377 ; while(y.name[++i] != 0); 378 ; if((off+i+2) > 511) prname(); 379 ; for(j=off+1; j>=0; --j) name[j+i+1] = name[j]; 380 ; off=i+off+1; 381 ; name[i] = root[0]; 382 ; for(--i; i>=0; --i) name[i] = y.name[i]; 383 ;} 384 385 cat: 386 00000185 31DB xor ebx, ebx 387 00000187 4B dec ebx ; i = -1 388 cat_0: 389 00000188 43 inc ebx ; ++i 390 00000189 80BB[88040000]00 cmp byte [yname+ebx], 0 391 00000190 77F6 ja short cat_0 392 00000192 89DA mov edx, ebx ; i 393 00000194 8B0D[3C040000] mov ecx, [off] 394 0000019A 41 inc ecx ; j = [off]+1 395 0000019B 01CA add edx, ecx ; edx = [off]+i+1 396 0000019D 81FAFD010000 cmp edx, 511-2 ; (+ CRLF + 0) 397 000001A3 779B ja short prname ; 14/05/2022 398 ;;ja short ckroot_2 ; jmp prname 399 ;ja short ckroot_err 400 000001A5 BE[38020000] mov esi, name 401 000001AA 01CE add esi, ecx ; name[j] 402 000001AC 89F7 mov edi, esi 403 000001AE 01DF add edi, ebx ; name[j+i] 404 000001B0 47 inc edi ; name[j+i+1] 405 cat_1: 406 ;std 407 ;rep stosb 408 ;cld 409 000001B1 49 dec ecx 410 000001B2 7808 js short cat_2 411 000001B4 4E dec esi 412 000001B5 8A06 mov al, [esi] 413 000001B7 4F dec edi 414 000001B8 8807 mov [edi], al 415 000001BA EBF5 jmp short cat_1 416 cat_2: 417 000001BC 8915[3C040000] mov [off], edx ; [off] = i+[off]+1 418 000001C2 C683[38020000]2F mov byte [name+ebx], '/' ; name[i] = root[0] 419 cat_3: 420 000001C9 4B dec ebx ; --i 421 000001CA 780E js short cat_4 ; 0 -> -1 422 ; name[i] = yname[i] 423 000001CC 8A83[88040000] mov al, [yname+ebx] 424 000001D2 8883[38020000] mov [name+ebx], al 425 000001D8 EBEF jmp short cat_3 ; i >= 0 426 cat_4: 427 000001DA C3 retn 428 429 ;----------------------------------------------------------------- 430 431 print_msg: 432 ; 08/05/2022 433 ; eax = asciiz string address 434 000001DB 89C2 mov edx, eax 435 000001DD 4A dec edx 436 nextchr: 437 000001DE 42 inc edx 438 000001DF 803A00 cmp byte [edx], 0 439 000001E2 77FA ja short nextchr 440 ;cmp [edx], 0Dh 441 ;ja short nextchr 442 000001E4 29C2 sub edx, eax 443 ; edx = asciiz string length 444 ; 445 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 446 ; 447 000001F4 C3 retn 448 449 ;----------------------------------------------------------------- 450 ; data - initialized data 451 ;----------------------------------------------------------------- 452 453 ; 05/05/2022 454 455 000001F5 2E dotdot: db '.' 456 000001F6 2E dot: db '.' 457 000001F7 00 db 0 458 459 ; 06/05/2022 460 nextline: 461 000001F8 0D0A db 0Dh, 0Ah 462 000001FA 2F00 root: db '/', 0 463 464 ; 14/05/2022 465 ; default mounting directories (for current retro unix version) 466 ;usr: db 'usr', 0 467 ;mnt: db 'mnt', 0 468 469 ; 14/05/2022 470 000001FC 0D0A err_0: db 0Dh, 0Ah 471 000001FE 4572726F7221 db "Error!" 472 00000204 0D0A00 db 0dh, 0Ah, 0 473 474 00000207 0D0A err_1: db 0Dh, 0Ah 475 00000209 7077643A2063616E20- db "pwd: can not open .." 475 00000212 6E6F74206F70656E20- 475 0000021B 2E2E 476 0000021D 0D0A00 db 0Dh, 0Ah, 0 477 00000220 0D0A err_2: db 0Dh, 0Ah 478 00000222 72656164206572726F- db "read error in .." 478 0000022B 7220696E202E2E 479 00000232 0D0A00 db 0Dh, 0Ah, 0 480 481 ;----------------------------------------------------------------- 482 ; bss - uninitialized data 483 ;----------------------------------------------------------------- 484 485 00000235 90 align 4 486 487 bss_start: 488 489 ABSOLUTE bss_start 490 491 ; 05/05/2022 492 493 00000238 name: resb 512 494 495 00000438 ???????? file: resd 1 496 0000043C ???????? off: resd 1 497 498 ; 14/05/2022 499 idev: 500 00000440 ???? d.dev: resw 1 ; device number (0 = root, 1 = mounted) 501 ;dd.dev: resw 1 502 503 _x: ; stat(us) buffer 504 _d: ; 14/05/2022 505 inum: 506 d.ino: ; 14/05/2022 507 00000442 ???? resw 1 508 ximode: 509 d.mode: ; 14/05/22022 510 ;resb 64 ; Retro UNIX 386 v1.2 511 00000444 resb 32 ; Retro UNIX 386 v1 & v1.1 512 513 ; 14/05/2022 514 _dd: ; stat(us) buffer 515 00000464 ???? dd.ino: resw 1 516 dd.mode: 517 00000466 resb 32 518 519 _y: ; directory entry buffer 520 00000486 ???? jnum: resw 1 521 00000488 yname: resb 14 ; Retro UNIX 386 v1.1 & v1.2 522 ;resb 8 ; Retro UNIX 386 v1 (unix v1) 523 00000496 ???? yzero: resw 1 524 525 ;----------------------------------------------------------------- 526 ; Original UNIX v7 - /bin/pwd file - c source code (pwd.c) 527 ;----------------------------------------------------------------- 528 ; 529 ;/* 530 ; * Print working (current) directory 531 ; */ 532 ;#include 533 ;#include 534 ;#include 535 ;#include 536 ; 537 ;char dot[] = "."; 538 ;char dotdot[] = ".."; 539 ;char name[512]; 540 ;int file; 541 ;int off = -1; 542 ;struct stat d, dd; 543 ;struct direct dir; 544 ; 545 ;main() 546 ;{ 547 ; int rdev, rino; 548 ; 549 ; stat("/", &d); 550 ; rdev = d.st_dev; 551 ; rino = d.st_ino; 552 ; for (;;) { 553 ; stat(dot, &d); 554 ; if (d.st_ino==rino && d.st_dev==rdev) 555 ; prname(); 556 ; if ((file = open(dotdot,0)) < 0) { 557 ; fprintf(stderr,"pwd: cannot open ..\n"); 558 ; exit(1); 559 ; } 560 ; fstat(file, &dd); 561 ; chdir(dotdot); 562 ; if(d.st_dev == dd.st_dev) { 563 ; if(d.st_ino == dd.st_ino) 564 ; prname(); 565 ; do 566 ; if (read(file, (char *)&dir, sizeof(dir)) < sizeof(dir)) { 567 ; fprintf(stderr,"read error in ..\n"); 568 ; exit(1); 569 ; } 570 ; while (dir.d_ino != d.st_ino); 571 ; } 572 ; else do { 573 ; if(read(file, (char *)&dir, sizeof(dir)) < sizeof(dir)) { 574 ; fprintf(stderr,"read error in ..\n"); 575 ; exit(1); 576 ; } 577 ; stat(dir.d_name, &dd); 578 ; } while(dd.st_ino != d.st_ino || dd.st_dev != d.st_dev); 579 ; close(file); 580 ; cat(); 581 ; } 582 ;} 583 ; 584 ;prname() 585 ;{ 586 ; write(1, "/", 1); 587 ; if (off<0) 588 ; off = 0; 589 ; name[off] = '\n'; 590 ; write(1, name, off+1); 591 ; exit(0); 592 ;} 593 ; 594 ;cat() 595 ;{ 596 ; register i, j; 597 ; 598 ; i = -1; 599 ; while (dir.d_name[++i] != 0); 600 ; if ((off+i+2) > 511) 601 ; prname(); 602 ; for(j=off+1; j>=0; --j) 603 ; name[j+i+1] = name[j]; 604 ; off=i+off+1; 605 ; name[i] = '/'; 606 ; for(--i; i>=0; --i) 607 ; name[i] = dir.d_name[i]; 608 ;} 609 610 ; 05/05/2022 611 612 ;----------------------------------------------------------------- 613 ; Original UNIX v5 - /usr/bin/pwd file - c source code (pwd.c) 614 ;----------------------------------------------------------------- 615 ; 616 ;char dot[] "."; 617 ;char dotdot[] ".."; 618 ;char root[] "/"; 619 ;char name[512]; 620 ;int file, off -1; 621 ;struct statb {int devn, inum, i[18];}x; 622 ;struct entry { int jnum; char name[16];}y; 623 ; 624 ;main() { 625 ; int n; 626 ; 627 ;loop0: 628 ; stat(dot, &x); 629 ; if((file = open(dotdot,0)) < 0) prname(); 630 ;loop1: 631 ; if((n = read(file,&y,16)) < 16) prname(); 632 ; if(y.jnum != x.inum)goto loop1; 633 ; close(file); 634 ; if(y.jnum == 1) ckroot(); 635 ; cat(); 636 ; chdir(dotdot); 637 ; goto loop0; 638 ;} 639 ;ckroot() { 640 ; int i, n; 641 ; 642 ; if((n = stat(y.name,&x)) < 0) prname(); 643 ; i = x.devn; 644 ; if((n = chdir(root)) < 0) prname(); 645 ; if((file = open(root,0)) < 0) prname(); 646 ;loop: 647 ; if((n = read(file,&y,16)) < 16) prname(); 648 ; if(y.jnum == 0) goto loop; 649 ; if((n = stat(y.name,&x)) < 0) prname(); 650 ; if(x.devn != i) goto loop; 651 ; x.i[0] =& 060000; 652 ; if(x.i[0] != 040000) goto loop; 653 ; cat(); 654 ; prname(); 655 ;} 656 ;prname() { 657 ; name[off] = '\n'; 658 ; write(1,name,off+1); 659 ; exit(); 660 ;} 661 ;cat() { 662 ; int i, j; 663 ; 664 ; i = -1; 665 ; while(y.name[++i] != 0); 666 ; if((off+i+2) > 511) prname(); 667 ; for(j=off+1; j>=0; --j) name[j+i+1] = name[j]; 668 ; off=i+off+1; 669 ; name[i] = root[0]; 670 ; for(--i; i>=0; --i) name[i] = y.name[i]; 671 ;}