浏览代码

Changed bulk send/receive to use system.move a block as large as possible. Merged.

git-svn-id: https://svn.inf.ethz.ch/svn/lecturers/a2/trunk@6916 8c9fc860-2736-0410-a75d-ab315db34111
skoster 9 年之前
父节点
当前提交
72b9407fca
共有 2 个文件被更改,包括 75 次插入24 次删除
  1. 67 16
      source/ActiveCellsRunner.mod
  2. 8 8
      source/ActiveCellsRuntime.mod

+ 67 - 16
source/ActiveCellsRunner.mod

@@ -18,14 +18,19 @@ type
 
 	Fifo=object
 	var
-		data: array 256 of system.byte;
-		inPos, outPos: longint; length: longint;
+		data: array 8*1024 of system.byte;   
+(*		inPos, outPos: longint; *)
+		length: longint;  
+		rdPos,numEle: longint;
 
 		inPort: Port; outPort: Port;
 
 		procedure &Init(outP: Port; inP: Port; length: longint);
 		begin
-			inPos := 0; outPos := 0; self.length := length;
+			(*inPos := 0; outPos := 0; *)
+			rdPos:=0; 
+			numEle:=0;
+			self.length := length; (*for some reason this is -1 usually. don't trust it!*)
 			assert(length < len(data));
 			inPort := inP; outPort := outP;
 			inPort.SetFifo(self); outPort.SetFifo(self);
@@ -34,46 +39,92 @@ type
 		procedure Put(value: longint);
 		begin{EXCLUSIVE}
 			halt(100);(*broken+deprecated*)
-			(*wait for 4 bytes of free space*)
-			await( ( len(data)- ( (inPos-outPos  +len(data) ) mod len(data) ) )>= sizeof(longint));
-			system.move(addressof(value) , addressof(data[inPos]) , sizeof(longint) );
-			inPos := inPos+sizeof(longint);
-			inPos := inPos mod len(data);
 		end Put;
 
 		procedure Get(var value: longint);
 		begin{EXCLUSIVE}
 			halt(100); (*broken+deprecated*)
-			(*wait for 4 bytes of available data*)
-			await( (inPos - outPos  +len(data) ) mod len(data) >= sizeof(longint));
-			system.move(addressof(data[outPos]) , addressof(value) ,  sizeof(longint) );
-			outPos:=outPos+sizeof(longint);
-			outPos := outPos mod len(data);
 		end Get;
 
 
 		(*todo: instead of looping byte by byte, figure out how much we can safely copy over and just do that.*)
 		procedure BulkPut(const value: array of system.byte);
 		var i: longint;
+		numCopy, writePos: longint;
 		begin{EXCLUSIVE}
 			(*because of the exclusive semantics, this bulk put will fill the entire buffer before any get operation has a chance to run*)
+			
+			i:=0;
+			while i<len(value) do
+				await(numEle<len(data));
+				writePos:=(rdPos+numEle) mod len(data);
+				
+				numCopy:= len(data)-numEle;  (*total free space*)
+				numCopy:= min( numCopy, len(data)- writePos);(* if free space wraps around, only copy into space from write  pointer to top*)
+				numCopy :=min(numCopy,len(value)-i ); (*copy at most as much data as is left over.*)
+				(*trace(i,rdPos,writePos,numCopy,numEle,len(value),len(data));*)
+				
+				system.move(addressof(  value[i] ) , addressof ( data[writePos] ), numCopy) ;
+				numEle:=numEle+numCopy;
+				i:=i+numCopy;
+			end;
+			
+			(*
+			(*confirmed working using lengths*)
 			for i:=0 to len(value)-1 do
+				await(numEle<len(data));
+				data[(rdPos+numEle) mod len(data)]:=value[i];
+				inc(numEle);
+			end;*)
+		
+			(*
+			(*old version using pointer comparision. effectively makes the buffer 1 smaller than allocated *)
+			for i:=0 to len(value)-1 do  
 				await((inPos+1) mod len(data) # outPos);
 				data[inPos]:=value[i];
 				inc(inPos); inPos := inPos mod len(data);
-			end;
+			end;			
+			*)
+			
 		end BulkPut;
 
 		procedure BulkGet(var value: array of system.byte);
 		var
+		
 			i: longint;
+			numCopy: longint;
 		begin{EXCLUSIVE}
 			(*because of the exclusive semantics, this bulk get will empty the entire buffer before any put operation has a chance to run*)
+			
+			i:=0; (*pointer into the value array of the receiver*)
+			while i<len(value) do
+				await(numEle>0);
+				numCopy:= min(numEle, len(data)-rdPos); (*total valid data or until it wraps around*)
+				numCopy:=min(numCopy,len(value)-i); (*don't copy more than there's space in the receiver*)
+				(*trace(i,rdPos,numCopy,numEle,len(value),len(data));*)
+				
+				system.move( addressof(data[rdPos]), addressof(value[i]),numCopy);
+				rdPos:=(rdPos+numCopy) mod len(data);
+				numEle:=numEle-numCopy;
+				i:=i+numCopy;
+			end;
+			
+			(*(*confirmed working using lengths*)
+			for i:=0 to len(value) -1 do
+				await(numEle>0);
+				value[i]:=data[rdPos];
+				inc(rdPos);rdPos:=rdPos mod len(data);
+				dec(numEle);
+			end;*)
+			
+			(*
+			(*old version using pinter comparison. effectively makes the buffer 1 smaller than allocated*)
 			for i:=0 to len(value)-1 do
 				await(inPos#outPos);
 				value[i]:=data[outPos];
 				inc(outPos);outPos:=outPos mod len(data);
-			end;
+			end;*)
+			
 		end BulkGet;
 
 	end Fifo;
@@ -169,7 +220,7 @@ type
 			if res # 0 then return; end; (*! do not do anything in case of an error *)
 			new(cel); c := cel;
 			cel.isCellnet := isCellnet;
-			if scope # nil then cel.scope := scope(Cell); end;
+			(*if scope # nil then cel.scope := scope(Cell); end;*)
 		end Allocate;
 
 		procedure AddPort*(c: any; var p: any; const name: array of char; inout: set; width: longint);

+ 8 - 8
source/ActiveCellsRuntime.mod

@@ -394,13 +394,13 @@ type
 			begin
 				Start(c, p)
 			end P;
-		end Starter
+		end Starter;
 				
 	var
 		moduleName, typeName, name: array 256 of char;
 		m: Modules.Module;
 		typeInfo: Modules.TypeDesc;
-		i, res: longint;
+		i, res: longint; 
 		str: array 256 of char;
 		scope: Cell;
 		unloaded: longint;
@@ -478,14 +478,14 @@ type
 	type bytearray= array of system.byte; 
 	operator "<<"* (p: port out; const a: bytearray);
 	begin
-		if EnableTrace then trace('bulk send'); end;
+		if EnableTrace then trace('bulk send',len(a)); end;
 		BulkSend(system.val(any,p),a);
 	end "<<";
 	
 	
 	operator "<<"* (var  a: bytearray; p: port in);
 	begin
-		if EnableTrace then trace('bulk rec');end;
+		if EnableTrace then trace('bulk rec',len(a));end;
 		BulkReceive(system.val(any,p),a);
 	end "<<";
 	
@@ -493,26 +493,26 @@ type
 	type longintSpecial= longint; 
 	operator "<<"* (p: port out; a: longintSpecial);
 	begin
-		if EnableTrace then trace('normal send');end;
+		if EnableTrace then trace('longint send');end;
 		BulkSend(system.val(any,p),a);
 	end "<<";
 	
 	operator "<<"* (var  a: longintSpecial; p: port in); 
 	begin
-		if EnableTrace then trace('normal rec');end;
+		if EnableTrace then trace('longint rec');end;
 		BulkReceive(system.val(any,p),a);
 	end "<<";
 
 	type realSpecial= real;
 	operator "<<"* (p: port out; a: realSpecial);
 	begin
-		if EnableTrace then trace('normal send');end;
+		if EnableTrace then trace('real send');end;
 		BulkSend(system.val(any,p),a);
 	end "<<";
 	
 	operator "<<"* (var  a:realSpecial; p: port in); 
 	begin
-		if EnableTrace then trace('normal rec');end;
+		if EnableTrace then trace('real rec');end;
 		BulkReceive(system.val(any,p),a);
 	end "<<";