// BFS Write
// New Alto basic file system

// Last modified September 25, 1982  3:05 PM by Taft


// Outgoing procedures
external [
	ReadDiskKd;
	WriteDiskKd;
	]

// incoming procedures
external [
	ReadVec;
	DumpCore;
	move;
	hpalloca;
	hpfree;
	RW;
	]

// incoming statics
external [
	diskKd;
	fpDiskDescriptor;
	diskBTsize;
	RealDA;
	errhlta;
	DCwrite;
	]

// Outgoing statics
external [
	crefKd
	daPgn1Kd
	]

// Outgoing statics
static [
	crefKd
	daPgn1Kd
	]

// declarations for the disk allocation bit table
// the DA structure declaration is also used


get "BFS.DEF"
get "altofilesys.d"


// Bravo "knows" that the bit table immediately follows the KDH structure.
// Warning: a copy of this structure lives in BFSWrite.sr.
structure KD:
	[
		[
		@KDH
		diskBitTable word 0
		] =
		[
		blank word (offset KDH.lastSn + size KDH.lastSn)/16
		bitTableChanged word  // pre-OS18 convention, which Bravo still uses
		]
	]

// R E A D  D I S K  K D
//
let ReadDiskKd() be
[
if crefKd eq 0 then
	[ let tsizKd = lKDHeader+diskBTsize;
	diskKd = hpalloca(tsizKd)
	let cfa = vec lCFA; move(fpDiskDescriptor,cfa,lFP)
	cfa >> CFA.fa.pageNumber = 0; cfa >> CFA.fa.charPos = 0;
	cfa >> CFA.fa.da = RealDA(cfa >> CFA.fp.leaderVirtualDa); 
	ReadVec(cfa,tsizKd,diskKd);
	unless diskBTsize eq diskKd >> KDH.diskBTsize then errhlta(49);
	diskKd >> KD.bitTableChanged = false;
	]
crefKd = crefKd+1;
]

// W R I T E  D I S K  K D
//
and WriteDiskKd() be
[
crefKd = crefKd-1;
if (crefKd eq 0) then
	[ if diskKd >> KD.bitTableChanged then
		[ diskKd >> KD.bitTableChanged = false;
		let tsizKd = lKDHeader+diskBTsize;
		let cfa = vec lCFA; move(fpDiskDescriptor,cfa,lFP)
		cfa >> CFA.fa.pageNumber = 1; cfa >> CFA.fa.charPos = 0;
		cfa >> CFA.fa.da = daPgn1Kd; 
		RW(cfa,tsizKd,diskKd, DCwrite);
		]
	hpfree(diskKd);
	diskKd = 0;
	]
]