/// <summary> /// Allocate an object pointer. /// </summary> /// <param name="size">The size of object properties.</param> /// <param name="metadata">Object type</param> /// <returns></returns> public StackValue AllocatePointer(int size, MetaData metadata) { int index = AllocateInternal(size, PrimitiveType.kTypePointer); var hpe = heapElements[index]; hpe.MetaData = metadata; return StackValue.BuildPointer(index, metadata); }
/// <summary> /// Sweep all heap elements that are marked as white. /// </summary> private void Sweep() { foreach (var ptr in sweepSet) { var hp = heapElements[ptr]; if (hp.Mark != GCMark.White) { continue; } if (hp is DSString) { stringTable.TryRemoveString(ptr); } else if (hp is DSObject) { var objPointer = StackValue.BuildPointer(ptr, hp.MetaData); isDisposing = true; GCDisposeObject(objPointer, executive); isDisposing = false; } totalAllocated -= hp.MemorySize; heapElements[ptr] = null; freeList.Add(ptr); } gcDebt = totalAllocated > GC_THRESHOLD ? totalAllocated : GC_THRESHOLD; }
/// <summary> /// Allocate an object pointer. /// </summary> /// <param name="values">Values of object properties</param> /// <param name="metaData">Object type</param> /// <returns></returns> private StackValue AllocatePointer(StackValue[] values, MetaData metaData) { int index = AllocateInternal(values, PrimitiveType.Pointer); var heapElement = heapElements[index]; heapElement.MetaData = metaData; return(StackValue.BuildPointer(index, metaData)); }
/// <summary> /// Allocate an object pointer. /// </summary> /// <param name="values">Values of object properties</param> /// <param name="metaData">Object type</param> /// <returns></returns> public StackValue AllocatePointer(IEnumerable <StackValue> values, MetaData metaData) { int index = AllocateInternal(values); var heapElement = heapElements[index]; heapElement.MetaData = metaData; return(StackValue.BuildPointer(index, metaData)); }
private void GCDisposeObject(StackValue svPtr, Executive exe) { int classIndex = svPtr.metaData.type; if (this.disposeProcedureNode == null || classIndex != previousClassIndex) { previousClassIndex = classIndex; ClassNode cn = exe.exe.classTable.ClassNodes[classIndex]; isDSObject = !string.IsNullOrEmpty(cn.ExternLib) && cn.ExternLib.Contains(".ds"); disposeProcedureNode = cn.GetDisposeMethod(); while (disposeProcedureNode == null) { if (cn.Base != Constants.kInvalidIndex) { classIndex = cn.Base; cn = exe.exe.classTable.ClassNodes[classIndex]; disposeProcedureNode = cn.GetDisposeMethod(); } else { break; } } } //legacy dispose for design script objects. This may be very rare if (disposeProcedureNode != null && isDSObject) { // TODO Jun/Jiong: Use build pointer utilities exe.rmem.Push(StackValue.BuildArrayDimension(0)); exe.rmem.Push(StackValue.BuildPointer(svPtr.Pointer, svPtr.metaData)); exe.rmem.Push(StackValue.BuildInt(1)); ++exe.RuntimeCore.FunctionCallDepth; // TODO: Need to move IsExplicitCall to DebugProps and come up with a more elegant solution for this // fix for IDE-963 - pratapa bool explicitCall = exe.IsExplicitCall; bool tempFlag = explicitCall; exe.Callr(disposeProcedureNode.RuntimeIndex, disposeProcedureNode.ID, classIndex, ref explicitCall); exe.IsExplicitCall = tempFlag; --exe.RuntimeCore.FunctionCallDepth; } else if (disposeProcedureNode != null) { exe.CallDispose(disposeProcedureNode, svPtr, classIndex); } }
/// <summary> /// Allocate an object pointer. /// /// Exceptions: ProtoCore.Exceptions.RunOutOfMemoryException /// </summary> /// <param name="size">The size of object properties.</param> /// <param name="metadata">Object type</param> /// <returns></returns> public StackValue AllocatePointer(int size, MetaData metadata) { try { int index = AllocateInternal(size, PrimitiveType.Pointer); var hpe = heapElements[index]; hpe.MetaData = metadata; return(StackValue.BuildPointer(index, metadata)); } catch (OutOfMemoryException) { throw new RunOutOfMemoryException(); } }
public StackFrame(int globalOffset) { Init(StackValue.BuildPointer(Constants.kInvalidPointer), Constants.kInvalidIndex, Constants.kInvalidIndex, Constants.kInvalidIndex, Constants.kInvalidIndex, 0, StackFrameType.LanguageBlock, StackFrameType.LanguageBlock, Constants.kInvalidIndex, globalOffset, Constants.kInvalidIndex, StackValue.BuildInvalidRegisters(), 0); }
private void GCDisposeObject(ref StackValue svPtr, Executive exe) { int classIndex = svPtr.metaData.type; ClassNode cn = exe.exe.classTable.ClassNodes[classIndex]; ProcedureNode pn = null; while (pn == null) { pn = cn.GetDisposeMethod(); if (pn == null && cn.baseList != null && cn.baseList.Count != 0) // search the base class { // assume multiple inheritance is not allowed // it will only has a single base class classIndex = cn.baseList[0]; cn = exe.exe.classTable.ClassNodes[cn.baseList[0]]; } else { break; } } if (pn != null) { // TODO Jun/Jiong: Use build pointer utilities exe.rmem.Push(StackValue.BuildArrayDimension(0)); exe.rmem.Push(StackValue.BuildPointer(svPtr.opdata, svPtr.metaData)); exe.rmem.Push(StackValue.BuildBlockIndex(pn.runtimeIndex)); exe.rmem.Push(StackValue.BuildArrayDimension(0)); exe.rmem.Push(StackValue.BuildStaticType((int)ProtoCore.PrimitiveType.kTypeVar)); ++exe.Core.FunctionCallDepth; // TODO: Need to move isExplicitCall to DebugProps and come up with a more elegant solution for this // fix for IDE-963 - pratapa bool explicitCall = exe.isExplicitCall; bool tempFlag = explicitCall; exe.Callr(pn.procId, classIndex, 1, ref explicitCall); exe.isExplicitCall = tempFlag; --exe.Core.FunctionCallDepth; } }
private void GCDisposeObject(StackValue svPtr, Executive exe) { int classIndex = svPtr.metaData.type; ClassNode cn = exe.exe.classTable.ClassNodes[classIndex]; ProcedureNode pn = cn.GetDisposeMethod(); while (pn == null) { if (cn.baseList != null && cn.baseList.Count != 0) { classIndex = cn.baseList[0]; cn = exe.exe.classTable.ClassNodes[classIndex]; pn = cn.GetDisposeMethod(); } else { break; } } if (pn != null) { // TODO Jun/Jiong: Use build pointer utilities exe.rmem.Push(StackValue.BuildArrayDimension(0)); exe.rmem.Push(StackValue.BuildPointer(svPtr.opdata, svPtr.metaData)); exe.rmem.Push(StackValue.BuildArrayDimension(0)); exe.rmem.Push(StackValue.BuildStaticType((int)PrimitiveType.kTypeVar)); exe.rmem.Push(StackValue.BuildInt(1)); ++exe.RuntimeCore.FunctionCallDepth; // TODO: Need to move IsExplicitCall to DebugProps and come up with a more elegant solution for this // fix for IDE-963 - pratapa bool explicitCall = exe.IsExplicitCall; bool tempFlag = explicitCall; exe.Callr(pn.runtimeIndex, pn.procId, classIndex, ref explicitCall); exe.IsExplicitCall = tempFlag; --exe.RuntimeCore.FunctionCallDepth; } }
public void GCMarkAndSweep(List<StackValue> rootPointers, Executive exe) { if (IsGCRunning) return; try { IsGCRunning = true; // Mark var count = heapElements.Count; var markBits = new BitArray(count); foreach (var index in fixedHeapElements) { markBits.Set(index, true); } var workingStack = new Stack<StackValue>(rootPointers); while (workingStack.Any()) { var pointer = workingStack.Pop(); var ptr = (int)pointer.RawIntValue; if (!pointer.IsReferenceType || markBits.Get(ptr)) { continue; } markBits.Set(ptr, true); var heapElement = heapElements[ptr]; IEnumerable<StackValue> subElements = Enumerable.Empty<StackValue>(); if (pointer.IsArray) { var array = ToHeapObject<DSArray>(pointer); var dict = array.ToDictionary(); subElements = subElements.Concat(dict.Keys).Concat(dict.Values); } else { subElements = heapElement.Values; } foreach (var subElement in subElements) { if (subElement.IsReferenceType && !markBits.Get((int)subElement.RawIntValue)) { workingStack.Push(subElement); } } } // Sweep for (int i = 0; i < count; ++i) { if (markBits.Get(i) || heapElements[i] == null) { continue; } var metaData = heapElements[i].MetaData; if (metaData.type == (int)PrimitiveType.kTypeString) { stringTable.TryRemoveString(i); } else if (metaData.type >= (int)PrimitiveType.kMaxPrimitives) { var objPointer = StackValue.BuildPointer(i, metaData); GCDisposeObject(objPointer, exe); } heapElements[i] = null; #if !HEAP_VERIFICATION freeList.Add(i); #endif } } finally { IsGCRunning = false; } }
public void GCMarkAndSweep(List <StackValue> rootPointers, Executive exe) { if (isGarbageCollecting) { return; } try { isGarbageCollecting = true; // Mark var count = heapElements.Count; var markBits = new BitArray(count); var workingStack = new Stack <StackValue>(rootPointers); while (workingStack.Any()) { var pointer = workingStack.Pop(); var ptr = (int)pointer.RawIntValue; if (!pointer.IsReferenceType || markBits.Get(ptr)) { continue; } markBits.Set(ptr, true); var heapElement = heapElements[ptr]; var subElements = heapElement.VisibleItems; if (heapElement.Dict != null) { subElements = subElements.Concat(heapElement.Dict.Keys) .Concat(heapElement.Dict.Values); } foreach (var subElement in subElements) { if (subElement.IsReferenceType && !markBits.Get((int)subElement.RawIntValue)) { workingStack.Push(subElement); } } } // Sweep for (int i = 0; i < count; ++i) { if (markBits.Get(i) || heapElements[i] == null) { continue; } var metaData = heapElements[i].MetaData; if (metaData.type >= (int)PrimitiveType.kMaxPrimitives) { var objPointer = StackValue.BuildPointer(i, metaData); GCDisposeObject(objPointer, exe); } heapElements[i] = null; #if !HEAP_VERIFICATION freeList.Add(i); #endif } } finally { isGarbageCollecting = false; } }
public StackValue AllocatePointer(int size, MetaData metadata) { int index = AllocateInternal(size); return(StackValue.BuildPointer(index, metadata)); }
public StackValue AllocatePointer(int size) { int index = AllocateInternal(size); return(StackValue.BuildPointer(index)); }