liquid-funding/contracts/EternallyPersistentLib.sol

176 lines
6.5 KiB
Solidity

pragma solidity ^0.4.0;
import "./EternalStorage.sol";
library EternallyPersistentLib {
// UInt
function stgObjectGetUInt(EternalStorage _storage, string class, uint id, string fieldName) internal view returns (uint) {
bytes32 record = keccak256(class, id, fieldName);
return _storage.getUIntValue(record);
}
function stgObjectSetUInt(EternalStorage _storage, string class, uint id, string fieldName, uint value) internal {
bytes32 record = keccak256(class, id, fieldName);
return _storage.setUIntValue(record, value);
}
// Boolean
function stgObjectGetBoolean(EternalStorage _storage, string class, uint id, string fieldName) internal view returns (bool) {
bytes32 record = keccak256(class, id, fieldName);
return _storage.getBooleanValue(record);
}
function stgObjectSetBoolean(EternalStorage _storage, string class, uint id, string fieldName, bool value) internal {
bytes32 record = keccak256(class, id, fieldName);
return _storage.setBooleanValue(record, value);
}
// string
function stgObjectGetString(EternalStorage _storage, string class, uint id, string fieldName) internal view returns (string) {
bytes32 record = keccak256(class, id, fieldName);
bytes4 sig = bytes4(keccak256("getStringValue(bytes32)"));
//Function signature
address a = address(_storage);
string memory s;
assembly {
let x := mload(0x40) //Find empty storage location using "free memory pointer"
mstore(x, sig) //Place signature at begining of empty storage
mstore(add(x, 0x04), record) //Place first argument directly next to signature
let success := call(//This is the critical change (Pop the top stack value)
5000, //5k gas
a, //To addr
0, //No value
x, //Inputs are stored at location x
0x24, //Inputs are 36 byes long
x, //Store output over input (saves space)
0x80) //Outputs are 32 bytes long
let strL := mload(add(x, 0x20)) // Load the length of the sring
jumpi(ask_more, gt(strL, 64))
mstore(0x40, add(x, add(strL, 0x40)))
s := add(x, 0x20)
// return(x, add(strL, 0x40))
ask_more :
mstore(x, sig) //Place signature at begining of empty storage
mstore(add(x, 0x04), record) //Place first argument directly next to signature
success := call(//This is the critical change (Pop the top stack value)
5000, //5k gas
a, //To addr
0, //No value
x, //Inputs are stored at location x
0x24, //Inputs are 36 byes long
x, //Store output over input (saves space)
add(0x40, strL)) //Outputs are 32 bytes long
mstore(0x40, add(x, add(strL, 0x40)))
s := add(x, 0x20)
// return(x, add(strL, 0x40))
}
return s;
}
function stgObjectSetString(EternalStorage _storage, string class, uint id, string fieldName, string value) internal {
bytes32 record = keccak256(class, id, fieldName);
return _storage.setStringValue(record, value);
}
// address
function stgObjectGetAddress(EternalStorage _storage, string class, uint id, string fieldName) internal view returns (address) {
bytes32 record = keccak256(class, id, fieldName);
return _storage.getAddressValue(record);
}
function stgObjectSetAddress(EternalStorage _storage, string class, uint id, string fieldName, address value) internal {
bytes32 record = keccak256(class, id, fieldName);
return _storage.setAddressValue(record, value);
}
// bytes32
function stgObjectGetBytes32(EternalStorage _storage, string class, uint id, string fieldName) internal view returns (bytes32) {
bytes32 record = keccak256(class, id, fieldName);
return _storage.getBytes32Value(record);
}
function stgObjectSetBytes32(EternalStorage _storage, string class, uint id, string fieldName, bytes32 value) internal {
bytes32 record = keccak256(class, id, fieldName);
return _storage.setBytes32Value(record, value);
}
// Array
// function stgCollectionAddItem(bytes32 idArray, bytes32 idItem) internal returns (uint64) {
function stgCollectionAddItem(EternalStorage _storage, bytes32 idArray) internal returns (uint) {
uint length = _storage.getUIntValue(keccak256(idArray, "length"));
// Set the position in the array as a field so it can be deleted
// _storage.setUIntValue(keccak256(idArray, idItem, "_idx"), length);
// Add the object to the array
// _storage.setBytes32Value(keccak256(idArray, length), idItem);
// Increment the size of the array
length++;
_storage.setUIntValue(keccak256(idArray, "length"), length);
return length;
}
// function stgCollectionRemoveItem(EternalStorage _storage, bytes32 idArray, bytes32 idItem) internal {
// uint idx = _storage.getUIntValue(keccak256(idArray, idItem, "_idx"));
//
// uint length = _storage.getUIntValue(keccak256(idArray, "length"));
// length --;
//
// // Move the last element ot the array to this place
// bytes32 lastId = _storage.getBytes32Value(keccak256(idArray, length));
// _storage.setBytes32Value(keccak256(idArray, idx), lastId);
// _storage.setUIntValue(keccak256(idArray, lastId, "_idx"), idx);
//
//
// // Decrement the length
// _storage.setUIntValue(keccak256(idArray, "length"), length);
//
// // Cleanup the last element of the array
// _storage.setBytes32Value(keccak256(idArray, length), 0);
//
// _storage.setUIntValue(keccak256(idArray, idItem, "_idx"), 0);
// }
function stgCollectionLength(EternalStorage _storage, bytes32 idArray) internal view returns (uint) {
return _storage.getUIntValue(keccak256(idArray, "length"));
}
function stgCollectionIdFromIdx(EternalStorage _storage, bytes32 idArray, uint idx) internal view returns (bytes32) {
return _storage.getBytes32Value(keccak256(idArray, idx));
}
// bytes32 lastId;
// function stgGetNewId() internal returns (bytes32) {
// lastId = keccak256(lastId, now);
// return lastId;
// }
function stgUpgrade(EternalStorage _storage, address newContract) internal {
_storage.changeOwnership(newContract);
}
}