Traversing a directory tree is a core function of many utilities. (Ideally, of course, the OS should have provided a means to do this from the start, abstracted from the nitty-gritty of systems implementation. Now we are stuck with our 36 character directory-plus-filename length limit and that awkward file header.)
The recursive routine CountDir does exactly that and on the way collects some data on the sub tree. RTFC for details!
The utilty DirSize requires Qmenu (which, again requires Qdos + PE + the command OUTLN) + tk2, or simply SMSQ/E, although it should be easy enough to alter the program to do without any of that..
As it stands, the program should be EXecuted under SMSQ/E, or compiled before EXecuting under Qdos. Alternatively, the savvy tinkerer will need to make a few changes to get it running under SuperBASIC!
10 REMark $$chan=18 11 REMark $$stak=2048 12 : 13 REMark DirSize in harness 14 REMark V0.01, pjw, 2018 Nov 18, Uses Qmenu 15 : 16 ch = FOPEN(#0; "con_400x200a20x20") 17 CLS#ch 18 BORDER#ch; 1,4 19 OUTLN: REMark #ch; 400, 200, 20, 20 20 odr$ = DATAD$: REMark Keep original DATAD$ 21 dir$ = odr$: sub$ = '' 22 : 23 REPeat lp 24 DATA_USE dir$ & sub$: REMark DIR_SELECT$ uses DATAD$ for its default 25 dir$ = DIR_SELECT$('Dir Size') 26 DATA_USE odr$ 27 IF LEN(dir$) = 0: EXIT lp 28 : 29 IF LEN(dir$) > 5 THEN 30 sub$ = dir$(6 TO): dir$ = dir$(1 TO 5) 31 ELSE 32 sub$ = '' 33 END IF 34 : 35 REMark Init GLOBal counters 36 fil = 0 37 drc = 0 38 siz = 0 39 : 40 er = CountDir(dir$, sub$) 41 INK#ch; 7 42 PRINT#ch; 'Stats of'! dir$; sub$\\ 43 INK#ch; 4 44 PRINT#ch; 'Size =', CDEC$(siz, 14, 0)! 'b' 45 PRINT#ch; 'Dirs =', drc 46 PRINT#ch; 'Files =', fil\\ 47 PAUSE#ch 48 END REPeat lp 49 : 50 : 51 rem + ------------------------------------------------------------------------ + 52 rem |< Count Directory >| 53 rem + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + 54 rem | Tree size | 55 rem | | 56 rem | Go through a directory sub tree recursively counting all files and | 57 rem | directories encountered and add up their total size (including headers!) | 58 rem | | 59 rem | GLObal drc, fil, siz | 60 rem + ------------------------------------------------------------------------ + 61 rem | V0.01, pjw, 2014 May 18 | 62 rem | V0.04, pjw, 2018 Nov 18, simplified and generalised version | 63 rem + ------------------------------------------------------------------------ + 64 : 65 DEFine FuNction CountDir(fdv$, dir$) 66 LOCal cd, lp, er, fl, ps, l, ty%, nm$(36) 67 : 68 cd = FOP_DIR(fdv$ & dir$): IF cd < 0: RETurn cd 69 ps = 0: er = 0: fl = FLEN(#cd) 70 REPeat lp 71 IF ps >= fl: EXIT lp 72 GET#cd\ ps + 14; nm$ 73 IF LEN(nm$) > 0 THEN 74 BGET#cd\ ps + 5, ty% 75 IF ty% = 255 THEN 76 drc = drc + 1 77 er = CountDir(fdv$, nm$): IF er < 0: EXIT lp 78 ELSE 79 LGET#cd\ ps + 0, l: siz = siz + l 80 fil = fil + 1 81 END IF 82 END IF 83 ps = ps + 64 84 END REPeat lp 85 CLOSE#cd 86 RETurn er 87 END DEFine CountDir 88 : 89 :