From 6cd9ae4f462390a219b6825a2ec123aa39469edc Mon Sep 17 00:00:00 2001 From: aaronhance Date: Tue, 8 Feb 2022 21:28:47 +0000 Subject: [PATCH] Dynamic lists fixes and additions # Conflicts: # src/include/lists.pas --- src/include/lists.pas | 254 ++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 254 insertions(+) diff --git a/src/include/lists.pas b/src/include/lists.pas index 7ec1de2e..2935e76f 100644 --- a/src/include/lists.pas +++ b/src/include/lists.pas @@ -44,6 +44,19 @@ type ElementSize : uint32; end; + { Dynamic List } + + PDList = ^TDList; + TDList = record + Count : uint32; + Data : void; + ElementSize : uint32; + DataSize : uint32; + + end; + + { Dynamic List Iterator } + { String Linked List } procedure STRLL_Add(LinkedList : PLinkedListBase; str : pchar); @@ -66,6 +79,24 @@ function LL_Get(LinkedList : PLinkedListBase; idx : uint32) : Void; procedure LL_Free(LinkedList : PLinkedListBase); function LL_FromString(str : pchar; delimter : char) : PLinkedListBase; + +{ Dynamic List } + +function DL_New(ElementSize : uint32) : PDList; +function DL_Add(DList : PDList) : Void; +function DL_Delete(DList : PDList; idx : uint32) : boolean; +function DL_Size(DList : PDList) : uint32; +function DL_Set(DList : PDList; idx : uint32; elm : puint32) : boolean; +function DL_Get(DList : PDList; idx : uint32) : Void; +procedure DL_Free(DList : PDList); +function DL_IndexOf(DList : PDList; elm : puint32) : uint32; +function DL_Contains(DList : PDList; elm : puint32) : boolean; +function DL_Concat(DList1 : PDList; DList2 : PDList) : PDList; + + +{ Dynamic List Iterator } + + implementation uses @@ -351,4 +382,227 @@ begin end; end; +{ Dynamic List } + +function DL_New(ElementSize : uint32) : PDList; +var + DL : PDList; +begin + + DL := PDList(kalloc(sizeof(DL))); + DL^.ElementSize:= ElementSize; + DL^.count := 0; + + if ElementSize > 128 then begin + DL^.data := kalloc(ElementSize * 4); + Dl^.DataSize:= ElementSize * 4; + + end else if ElementSize > 64 then begin + DL^.data := kalloc(ElementSize * 8); + Dl^.DataSize:= ElementSize * 8; + + end else if ElementSize > 32 then begin + DL^.data := kalloc(ElementSize * 16); + Dl^.DataSize:= ElementSize * 16; + + end else if ElementSize > 16 then begin + DL^.data := kalloc(ElementSize * 32); + Dl^.DataSize:= ElementSize * 32; + end else begin + DL^.data := kalloc(ElementSize * 64); + Dl^.DataSize:= ElementSize * 64; + end; + + DL_New := DL; +end; + +function DL_Add(DList : PDList) : Void; +var + elm : puint32; + tempList : puint32; +begin + + //check if we need to resize + if (DList^.count + 1) * DList^.ElementSize > DList^.DataSize then begin + push_trace('lists.DL_Add: Resizing'); + tempList := DList^.Data; + DList^.Data := kalloc(DList^.DataSize * 2); + + memset(uint32(DList^.Data), 0, DList^.DataSize * 2); + memcpy(uint32(tempList), uint32(DList^.Data), DList^.DataSize); + + DList^.DataSize:= DList^.DataSize * 2; + + kfree(void(tempList)); + end; + + push_trace('lists.DL_Add'); + + + elm := puint32(@puint8(DList^.Data)[(DList^.count * DList^.ElementSize)]); + elm^ := 0; + + push_trace('lists.DL_Add: Adding'); + + DList^.count := DList^.count + 1; + + DL_Add := elm; +end; + +function DL_Delete(DList : PDList; idx : uint32) : boolean; +var + elm : puint32; + tempList : puint32; +begin + if idx >= DList^.count then begin + DL_Delete := false; + exit; + end; + + elm := puint32( puint8(DList^.Data) + (idx * DList^.ElementSize)); + memcpy(uint32( puint8(elm) + DList^.ElementSize), uInt32(elm), (DList^.count - idx) * DList^.ElementSize); + + DList^.count := DList^.count - 1; + + if (DList^.count * DList^.ElementSize) < DList^.DataSize DIV 2 then begin + tempList := DList^.Data; + DList^.DataSize:= DList^.DataSize DIV 2; + + DList^.Data := kalloc(DList^.DataSize); + memcpy(uint32(tempList), uint32(DList^.Data), DList^.DataSize); + + kfree(void(tempList)); + end; + + DL_Delete := true; +end; + +function DL_Get(DList : PDList; idx : uint32) : Void; +var + elm : puint32; +begin + if idx >= DList^.count then begin + DL_Get := nil; + exit; + end; + + elm := puint32(DList^.Data + (idx * DList^.ElementSize)); + DL_Get := elm; +end; + +function DL_Set(DList : PDList; idx : uint32; elm : puint32) : boolean; +var + tempList : PuInt32; + size : uint32; +begin + if idx >= DList^.count then begin + DL_Set := false; + exit; + end; + + //check if we need to resize + if (idx + 1) * Dlist^.ElementSize > DList^.DataSize then begin + console.writestring('resising thisthinghere'); + + size := idx * DList^.ElementSize * 2; + + tempList := DList^.Data; + DList^.Data := kalloc(size); + memset(uint32(DList^.Data), 0, size); + + memcpy(uint32(tempList), uint32(DList^.Data), DList^.DataSize); + + DList^.DataSize := size; + + kfree(void(tempList)); + end; + + console.writeString('offset: '); + console.writeintln(idx * DList^.ElementSize); + memcpy(uint32(elm), uint32( PuInt8(DList^.Data) + (idx * DList^.ElementSize)), DList^.ElementSize); + + //check if count is smaller than idx and if so, increase count + if DList^.count < idx then DList^.count := idx; + + DL_Set := true; +end; + +function DL_Size(DList : PDList) : uint32; +begin + DL_Size := DList^.count; +end; + +procedure DL_Free(DList : PDList); +begin + kfree(void(DList^.Data)); + kfree(void(DList)); +end; + +function DL_IndexOf(DList : PDList; elm : puint32) : uint32; +var + i : uint32; + temp : puint32; +begin + for i := 0 to DList^.count - 1 do begin + temp := puint32( puint8(DList^.Data) + (i * DList^.ElementSize)); + if temp = elm then begin + DL_IndexOf := i; + exit; + end; + end; + + DL_IndexOf := -1; +end; + +function DL_Contains(DList : PDList; elm : puint32) : boolean; +var + i : uint32; +begin + i := DL_IndexOf(DList, elm); + + if i = -1 then begin + DL_Contains := false; + exit; + end; + + DL_Contains := true; +end; + +function DL_Concat(DList1 : PDList; DList2 : PDList) : PDList; +var + i : uint32; + temp : puint32; +begin + + //check element size + if DList1^.ElementSize <> DList2^.ElementSize then begin + DL_Concat := nil; + exit; + end; + + //check if we need to resize + while true do begin + if (DList1^.count + DList2^.count) * DList1^.ElementSize > DList1^.DataSize then begin + + temp := DList1^.Data; + DList1^.Data := kalloc(DList1^.DataSize * 2); + + memset(uint32(DList1^.Data), 0, DList1^.DataSize * 2); + memcpy(uint32(temp), uint32(DList1^.Data), DList1^.DataSize); + + DList1^.DataSize:= DList1^.DataSize * 2; + + kfree(void(temp)); + end else Break; + end; + + + for i := 0 to DList2^.count - 1 do begin + temp := DL_Add(DList1); + memcpy(uint32(DL_Get(DList2, i)), uint32(temp), DList1^.ElementSize); + end; + + DL_Concat := DList1; +end; + end. \ No newline at end of file