// File: /workspace/github_cpp_makefile_star2_O2/menhits[P]phplus/src/PhplusStdLib.cpp
// Function: populateArrayFuncs()
void populateArrayFuncs()
{
	TupleTypeMaker maker;
	maker.add("_size", Int);
	maker.add("_capacity", Int);
	maker.add("_data", Whatev->getPtr());
	Array=maker.get(false);
	
	addType(Array, "Array");
	
	globalNamespace->addNode(
		AstWhatevToActionFactory::make(
			[](Type leftType, Type rightType) -> Action
			{
				assert leftType->isCreatable() && rightType->isVoid()
					otherwise return nullptr;
				
				Type contentsType=leftType;
				Type arrayType=Array->actuallyIs(makeTuple({{"a", Int}, {"b", Int}, {"c", contentsType->getPtr()}}, true))->getPtr();
				
				return lambdaAction(
					leftType,
					rightType,
					arrayType,
					
					[=](void* leftIn, void* rightIn) -> void*
					{
						void* out=malloc(arrayType->getSize());
						setValInTuple(out, arrayType, "_size", 0);
						setValInTuple(out, arrayType, "_capacity", 0);
						setValInTuple<void*>(out, arrayType, "_data", nullptr);
						return out;
					},
					
					[=](Action inLeft, Action inRight, CppProgram* prog)
					{
						throw PhplusError("not yet implemented", INTERNAL_ERROR);
					},
					
					"Array"
				);
			}
		),
		"Array"
	);
	
	globalNamespace->addNode(
		AstWhatevToActionFactory::make(
			[](Type leftType, Type rightType) -> Action
			{
				assert leftType->matches(Array)
					otherwise return nullptr;
				
				Type arrayType=Array->actuallyIs(leftType->getPtr());
				Type contentsType=arrayType->getSubType("_data").type->getSubType();
				
				assert rightType->matches(contentsType)
					otherwise return nullptr;
				
				return lambdaAction(
					leftType,
					rightType,
					Void,
					
					[=](void* leftIn, void* rightIn) -> void*
					{
						int size=getValFromTuple<int>(leftIn, arrayType, "_size");
						int capacity=getValFromTuple<int>(leftIn, arrayType, "_capacity");
						void* data=getValFromTuple<void*>(leftIn, arrayType, "_data");
						
						if (size+1>capacity)
						{
							if (capacity<1000)
								capacity=1000;
							else
								capacity*=2;
							
							setValInTuple<int>(leftIn, arrayType, "_capacity", capacity);
							void* newData=malloc(capacity*contentsType->getSize());
							memcpy(newData, data, size*contentsType->getSize());
							free(data);
							data=newData;
							setValInTuple<void*>(leftIn, arrayType, "_data", data);
						}
						
						setValInTuple<int>(leftIn, arrayType, "_size", size+1);
						memcpy((char*)data+size*contentsType->getSize(), rightIn, contentsType->getSize());
						
						return nullptr;
					},
					
					[=](Action inLeft, Action inRight, CppProgram* prog)
					{
						throw PhplusError("not yet implemented", INTERNAL_ERROR);
					},
					"append"
				);
			}
		),
		"append"
	);
	
	globalNamespace->addNode(
		AstWhatevToActionFactory::make(
			[](Type leftType, Type rightType) -> Action
			{
				assert leftType->matches(Array->getPtr()) && rightType->matches(Int)
					otherwise return nullptr;
				
				Type arrayType=Array->actuallyIs(leftType->getSubType());
				Type contentsType=arrayType->getSubType("_data").type->getSubType();
				size_t elemSize=contentsType->getSize();
				
				return lambdaAction(
					leftType,
					rightType,
					contentsType,
					
					[=](void* leftIn, void* rightIn) -> void*
					{
						int size=getValFromTuple<int>(leftIn, arrayType, "_size");
						if (*(int*)rightIn<0 || *(int*)rightIn>=size)
							throw PhplusError("index out of bounds, tried to get element at position "+to_string(*(int*)rightIn)+" in array "+to_string(size)+" long", RUNTIME_ERROR);
						
						void* out=malloc(contentsType->getSize());
						memcpy(out, getValFromTuple<char*>(leftIn, arrayType, "_data")+(*(int*)rightIn)*elemSize, elemSize);
						return out;
					},
					
					[=](Action inLeft, Action inRight, CppProgram* prog)
					{
						throw PhplusError("not yet implemented", INTERNAL_ERROR);
					},
					"get"
				);
			}
		),
		"get"
	);
	
	globalNamespace->addNode(
		AstWhatevToActionFactory::make(
			[](Type leftType, Type rightType) -> Action
			{
				Type arrayType=Array->actuallyIs(leftType->getSubType());
				Type contentsType=arrayType->getSubType("_data").type->getSubType();
				
				Type inputType=makeTuple({{"index", Int}, {"value", contentsType}}, true);
				
				assert leftType->getSubType()->matches(Array) && rightType->matches(inputType)
					otherwise return nullptr;
				
				size_t elemSize=contentsType->getSize();
				
				return lambdaAction(
					leftType,
					rightType,
					contentsType,
					
					[=](void* leftIn, void* rightIn) -> void*
					{
						int size=getValFromTuple<int>(leftIn, arrayType, "_size");
						int index=getValFromTuple<int>(rightIn, inputType, "index");
						
						if (index<0 || index>=size)
							throw PhplusError("index out of bounds, tried to set element at position "+to_string(index)+" in array "+to_string(size)+" long", RUNTIME_ERROR);
						
						char* data=getValFromTuple<char*>(leftIn, arrayType, "_data");
						
						memcpy(data+index*elemSize, (char*)rightIn+inputType->getSubType("value").offset, contentsType->getSize());
						
						return nullptr;
					},
					
					[=](Action inLeft, Action inRight, CppProgram* prog)
					{
						throw PhplusError("not yet implemented", INTERNAL_ERROR);
					},
					"set"
				);
			}
		),
		"set"
	);
	
	globalNamespace->addNode(
		AstWhatevToActionFactory::make(
			[](Type leftType, Type rightType) -> Action
			{
				assert leftType->matches(Array) && rightType->isVoid()
					otherwise return nullptr;
				
				Type arrayType=Array->actuallyIs(leftType);
				Type contentsType=arrayType->getSubType("_data").type->getSubType();
				
				return lambdaAction(
					leftType,
					rightType,
					Int,
					
					[=](void* leftIn, void* rightIn) -> void*
					{
						int* out=(int*)malloc(sizeof(int));
						*out=getValFromTuple<int>(leftIn, arrayType, "_size");
						return out;
					},
					
					[=](Action inLeft, Action inRight, CppProgram* prog)
					{
						throw PhplusError("not yet implemented", INTERNAL_ERROR);
					},
					"len"
				);
			}
		),
		"len"
	);
	
	globalNamespace->addNode(
		AstWhatevToActionFactory::make(
			[](Type leftType, Type rightType) -> Action
			{
				assert leftType->isVoid() && rightType->matches(Array)
					otherwise return nullptr;
				
				Type arrayType=Array->actuallyIs(rightType);
				Type contentsType=arrayType->getSubType("_data").type->getSubType();
				size_t elemSize=contentsType->getSize();
				
				return lambdaAction(
					Void,
					rightType,
					rightType,
					
					[=](void* leftIn, void* rightIn) -> void*
					{
						//error.log("Array destroyer called", JSYK);
						int size=getValFromTuple<int>(rightIn, arrayType, "_size");
						void* newData=malloc(elemSize*size);
						void* oldData=getValFromTuple<void*>(rightIn, arrayType, "_data");
						memcpy(newData, oldData, elemSize*size);
						setValInTuple(rightIn, arrayType, "_data", newData);
						void* out=malloc(arrayType->getSize());
						memcpy(out, rightIn, arrayType->getSize());
						return out;
					},
					
					[=](Action inLeft, Action inRight, CppProgram* prog)
					{
						throw PhplusError("not yet implemented", INTERNAL_ERROR);
					},
					"__copy__"
				);
			}
		),
		"__copy__"
	);
	
	globalNamespace->addNode(
		AstWhatevToActionFactory::make(
			[](Type leftType, Type rightType) -> Action
			{
				assert leftType->isVoid() && rightType->matches(Array)
					otherwise return nullptr;
				
				Type arrayType=Array->actuallyIs(rightType);
				
				return lambdaAction(
					Void,
					rightType,
					Void,
					
					[=](void* leftIn, void* rightIn) -> void*
					{
						//error.log("Array destroyer called", JSYK);
						
						free(getValFromTuple<void*>(rightIn, arrayType, "_data"));
						return nullptr;
					},
					
					[=](Action inLeft, Action inRight, CppProgram* prog)
					{
						throw PhplusError("not yet implemented", INTERNAL_ERROR);
					},
					"__destroy__"
				);
			}
		),
		"__destroy__"
	);
}

// Assembly:
pushq %rbx
subq $0x2d0, %rsp            # imm = 0x2D0
leaq 0x10(%rsp), %rdi
callq 0x3e21a
leaq 0x2aae3(%rip), %rsi     # 0x57b1c
leaq 0x1d0(%rsp), %rdi
movq %rsp, %rdx
callq 0xa150
leaq 0x4d3d0(%rip), %rsi     # 0x7a420
leaq 0x80(%rsp), %rbx
movq %rbx, %rdi
callq 0x12c0a
leaq 0x10(%rsp), %rdi
leaq 0x1d0(%rsp), %rsi
movq %rbx, %rdx
callq 0x3e26e
leaq 0x88(%rsp), %rdi
callq 0xc984
leaq 0x1d0(%rsp), %rdi
callq 0xa558
leaq 0x2acbc(%rip), %rsi     # 0x57d52
leaq 0x1b0(%rsp), %rdi
movq %rsp, %rdx
callq 0xa150
leaq 0x4d373(%rip), %rsi     # 0x7a420
leaq 0x70(%rsp), %rbx
movq %rbx, %rdi
callq 0x12c0a
leaq 0x10(%rsp), %rdi
leaq 0x1b0(%rsp), %rsi
movq %rbx, %rdx
callq 0x3e26e
leaq 0x78(%rsp), %rdi
callq 0xc984
leaq 0x1b0(%rsp), %rdi
callq 0xa558
leaq 0x2adca(%rip), %rsi     # 0x57eb7
leaq 0x190(%rsp), %rdi
movq %rsp, %rdx
callq 0xa150
leaq 0x4d2ec(%rip), %rax     # 0x7a3f0
movq (%rax), %rsi
leaq 0x60(%rsp), %rdi
callq 0x3dce8
leaq 0x10(%rsp), %rdi
leaq 0x190(%rsp), %rsi
leaq 0x60(%rsp), %rdx
callq 0x3e26e
leaq 0x68(%rsp), %rdi
callq 0xc984
leaq 0x190(%rsp), %rdi
callq 0xa558
movq %rsp, %rdi
leaq 0x10(%rsp), %rsi
xorl %edx, %edx
callq 0x3e5ae
leaq 0x4d23b(%rip), %rbx     # 0x7a390
movq %rsp, %rsi
movq %rbx, %rdi
callq 0x135a2
leaq 0x8(%rsp), %rdi
callq 0xc984
leaq 0x50(%rsp), %rdi
movq %rbx, %rsi
callq 0x12c0a
leaq 0x2a960(%rip), %rsi     # 0x57ade
leaq 0x170(%rsp), %rdi
movq %rsp, %rdx
callq 0xa150
leaq 0x50(%rsp), %rdi
leaq 0x170(%rsp), %rsi
callq 0x23237
leaq 0x170(%rsp), %rdi
callq 0xa558
leaq 0x58(%rsp), %rdi
callq 0xc984
movq 0x4d1a2(%rip), %rbx     # 0x7a360
xorps %xmm0, %xmm0
leaq 0x2b0(%rsp), %rsi
movaps %xmm0, (%rsi)
leaq 0x73a9(%rip), %rax      # 0x3457c
movq %rax, 0x18(%rsi)
leaq 0x77f8(%rip), %rax      # 0x349d6
movq %rax, 0x10(%rsi)
leaq 0x48(%rsp), %rdi
callq 0x3a28a
leaq 0x2a8eb(%rip), %rsi     # 0x57ade
leaq 0x150(%rsp), %rdi
movq %rsp, %rdx
callq 0xa150
leaq 0x48(%rsp), %rsi
leaq 0x150(%rsp), %rdx
movq %rbx, %rdi
callq 0x1c0f2
leaq 0x150(%rsp), %rdi
callq 0xa558
leaq 0x48(%rsp), %rdi
callq 0x11c58
leaq 0x2b0(%rsp), %rdi
callq 0x182be
movq 0x4d11d(%rip), %rbx     # 0x7a360
xorps %xmm0, %xmm0
leaq 0x290(%rsp), %rsi
movaps %xmm0, (%rsi)
leaq 0x7a4e(%rip), %rax      # 0x34ca6
movq %rax, 0x18(%rsi)
leaq 0x7e45(%rip), %rax      # 0x350a8
movq %rax, 0x10(%rsi)
leaq 0x40(%rsp), %rdi
callq 0x3a28a
leaq 0x2aae4(%rip), %rsi     # 0x57d5c
leaq 0x130(%rsp), %rdi
movq %rsp, %rdx
callq 0xa150
leaq 0x40(%rsp), %rsi
leaq 0x130(%rsp), %rdx
movq %rbx, %rdi
callq 0x1c0f2
leaq 0x130(%rsp), %rdi
callq 0xa558
leaq 0x40(%rsp), %rdi
callq 0x11c58
leaq 0x290(%rsp), %rdi
callq 0x182be
movq 0x4d098(%rip), %rbx     # 0x7a360
xorps %xmm0, %xmm0
leaq 0x270(%rsp), %rsi
movaps %xmm0, (%rsi)
leaq 0x82df(%rip), %rax      # 0x355bc
movq %rax, 0x18(%rsi)
leaq 0x8720(%rip), %rax      # 0x35a08
movq %rax, 0x10(%rsi)
leaq 0x38(%rsp), %rdi
callq 0x3a28a
leaq 0x2aa66(%rip), %rsi     # 0x57d63
leaq 0x110(%rsp), %rdi
movq %rsp, %rdx
callq 0xa150
leaq 0x38(%rsp), %rsi
leaq 0x110(%rsp), %rdx
movq %rbx, %rdi
callq 0x1c0f2
leaq 0x110(%rsp), %rdi
callq 0xa558
leaq 0x38(%rsp), %rdi
callq 0x11c58
leaq 0x270(%rsp), %rdi
callq 0x182be
movq 0x4d013(%rip), %rbx     # 0x7a360
xorps %xmm0, %xmm0
leaq 0x250(%rsp), %rsi
movaps %xmm0, (%rsi)
leaq 0x8aca(%rip), %rax      # 0x35e2c
movq %rax, 0x18(%rsi)
leaq 0x9067(%rip), %rax      # 0x363d4
movq %rax, 0x10(%rsi)
leaq 0x30(%rsp), %rdi
callq 0x3a28a
leaq 0x272e0(%rip), %rsi     # 0x54662
leaq 0xf0(%rsp), %rdi
movq %rsp, %rdx
callq 0xa150
leaq 0x30(%rsp), %rsi
leaq 0xf0(%rsp), %rdx
movq %rbx, %rdi
callq 0x1c0f2
leaq 0xf0(%rsp), %rdi
callq 0xa558
leaq 0x30(%rsp), %rdi
callq 0x11c58
leaq 0x250(%rsp), %rdi
callq 0x182be
movq 0x4cf8e(%rip), %rbx     # 0x7a360
xorps %xmm0, %xmm0
leaq 0x230(%rsp), %rsi
movaps %xmm0, (%rsi)
leaq 0x9521(%rip), %rax      # 0x36908
movq %rax, 0x18(%rsi)
leaq 0x98b0(%rip), %rax      # 0x36ca2
movq %rax, 0x10(%rsi)
leaq 0x28(%rsp), %rdi
callq 0x3a28a
leaq 0x2a941(%rip), %rsi     # 0x57d48
leaq 0xd0(%rsp), %rdi
movq %rsp, %rdx
callq 0xa150
leaq 0x28(%rsp), %rsi
leaq 0xd0(%rsp), %rdx
movq %rbx, %rdi
callq 0x1c0f2
leaq 0xd0(%rsp), %rdi
callq 0xa558
leaq 0x28(%rsp), %rdi
callq 0x11c58
leaq 0x230(%rsp), %rdi
callq 0x182be
movq 0x4cf09(%rip), %rbx     # 0x7a360
xorps %xmm0, %xmm0
leaq 0x210(%rsp), %rsi
movaps %xmm0, (%rsi)
leaq 0x9a36(%rip), %rax      # 0x36ea2
movq %rax, 0x18(%rsi)
leaq 0x9de7(%rip), %rax      # 0x3725e
movq %rax, 0x10(%rsi)
leaq 0x20(%rsp), %rdi
callq 0x3a28a
leaq 0x27eb1(%rip), %rsi     # 0x5533d
leaq 0xb0(%rsp), %rdi
movq %rsp, %rdx
callq 0xa150
leaq 0x20(%rsp), %rsi
leaq 0xb0(%rsp), %rdx
movq %rbx, %rdi
callq 0x1c0f2
leaq 0xb0(%rsp), %rdi
callq 0xa558
leaq 0x20(%rsp), %rdi
callq 0x11c58
leaq 0x210(%rsp), %rdi
callq 0x182be
movq 0x4ce84(%rip), %rbx     # 0x7a360
xorps %xmm0, %xmm0
leaq 0x1f0(%rsp), %rsi
movaps %xmm0, (%rsi)
leaq 0xa08d(%rip), %rax      # 0x3757e
movq %rax, 0x18(%rsi)
leaq 0xa36c(%rip), %rax      # 0x37868
movq %rax, 0x10(%rsi)
leaq 0x18(%rsp), %rdi
callq 0x3a28a
leaq 0x27e20(%rip), %rsi     # 0x55331
leaq 0x90(%rsp), %rdi
movq %rsp, %rdx
callq 0xa150
leaq 0x18(%rsp), %rsi
leaq 0x90(%rsp), %rdx
movq %rbx, %rdi
callq 0x1c0f2
leaq 0x90(%rsp), %rdi
callq 0xa558
leaq 0x18(%rsp), %rdi
callq 0x11c58
leaq 0x1f0(%rsp), %rdi
callq 0x182be
leaq 0x10(%rsp), %rdi
callq 0x12ede
addq $0x2d0, %rsp            # imm = 0x2D0
popq %rbx
retq
movq %rax, %rbx
leaq 0x90(%rsp), %rdi
callq 0xa558
jmp 0x2d582
movq %rax, %rbx
leaq 0x18(%rsp), %rdi
callq 0x11c58
jmp 0x2d591
movq %rax, %rbx
leaq 0x1f0(%rsp), %rdi
jmp 0x2d6b9
movq %rax, %rbx
leaq 0xb0(%rsp), %rdi
callq 0xa558
jmp 0x2d5b3
movq %rax, %rbx
leaq 0x20(%rsp), %rdi
callq 0x11c58
jmp 0x2d5c2
movq %rax, %rbx
leaq 0x210(%rsp), %rdi
jmp 0x2d6b9
movq %rax, %rbx
leaq 0xd0(%rsp), %rdi
callq 0xa558
jmp 0x2d5e4
movq %rax, %rbx
leaq 0x28(%rsp), %rdi
callq 0x11c58
jmp 0x2d5f3
movq %rax, %rbx
leaq 0x230(%rsp), %rdi
jmp 0x2d6b9
movq %rax, %rbx
leaq 0xf0(%rsp), %rdi
callq 0xa558
jmp 0x2d615
movq %rax, %rbx
leaq 0x30(%rsp), %rdi
callq 0x11c58
jmp 0x2d624
movq %rax, %rbx
leaq 0x250(%rsp), %rdi
jmp 0x2d6b9
movq %rax, %rbx
leaq 0x110(%rsp), %rdi
callq 0xa558
jmp 0x2d646
movq %rax, %rbx
leaq 0x38(%rsp), %rdi
callq 0x11c58
jmp 0x2d655
movq %rax, %rbx
leaq 0x270(%rsp), %rdi
jmp 0x2d6b9
movq %rax, %rbx
leaq 0x130(%rsp), %rdi
callq 0xa558
jmp 0x2d674
movq %rax, %rbx
leaq 0x40(%rsp), %rdi
callq 0x11c58
jmp 0x2d683
movq %rax, %rbx
leaq 0x290(%rsp), %rdi
jmp 0x2d6b9
movq %rax, %rbx
leaq 0x150(%rsp), %rdi
callq 0xa558
jmp 0x2d6a2
movq %rax, %rbx
leaq 0x48(%rsp), %rdi
callq 0x11c58
jmp 0x2d6b1
movq %rax, %rbx
leaq 0x2b0(%rsp), %rdi
callq 0x182be
leaq 0x10(%rsp), %rdi
callq 0x12ede
movq %rbx, %rdi
callq 0xa500
movq %rax, %rbx
leaq 0x170(%rsp), %rdi
callq 0xa558
jmp 0x2d6e5
movq %rax, %rbx
leaq 0x58(%rsp), %rdi
callq 0xc984
jmp 0x2d6be
jmp 0x2d74c
movq %rax, %rbx
leaq 0x68(%rsp), %rdi
callq 0xc984
jmp 0x2d705
movq %rax, %rbx
leaq 0x190(%rsp), %rdi
jmp 0x2d742
jmp 0x2d74c
movq %rax, %rbx
leaq 0x78(%rsp), %rdi
callq 0xc984
leaq 0x1b0(%rsp), %rdi
jmp 0x2d742
jmp 0x2d74c
movq %rax, %rbx
leaq 0x88(%rsp), %rdi
callq 0xc984
leaq 0x1d0(%rsp), %rdi
callq 0xa558
jmp 0x2d6be
movq %rax, %rbx
jmp 0x2d6be