github.com/inklabsfoundation/inkchain@v0.17.1-0.20181025012015-c3cef8062f19/examples/xc/qtum/contracts/XC.sol (about)

     1  pragma solidity ^0.4.19;
     2  
     3  import "./XCInterface.sol";
     4  
     5  import "./Token.sol";
     6  
     7  import "./XCPlugin.sol";
     8  
     9  import "./SafeMath.sol";
    10  
    11  contract XC is XCInterface {
    12  
    13      /**
    14       * Contract Administrator
    15       * @field status Contract external service status.
    16       * @field platformName Current contract platform name.
    17       * @field account Current contract administrator.
    18       */
    19      struct Admin {
    20  
    21          uint8 status;
    22  
    23          bytes32 platformName;
    24  
    25          address account;
    26      }
    27  
    28      Admin private admin;
    29  
    30      uint public lockBalance;
    31  
    32      Token private token;
    33  
    34      XCPlugin private xcPlugin;
    35  
    36      bytes2 private compareSymbol;
    37  
    38      event Lock(bytes32 toPlatform, address toAccount, string value);
    39  
    40      event Unlock(string txid, bytes32 fromPlatform, address fromAccount, string value);
    41  
    42      function XC() public payable {
    43          //TODO
    44          bytes32 name = "QTUM";
    45          //TODO
    46          compareSymbol = "-=";
    47  
    48          //TODO totalSupply = 10 * (10 ** 8) * (10 ** 9);
    49          lockBalance = 0;
    50  
    51          admin = Admin(0, name, msg.sender);
    52      }
    53  
    54      function setStatus(uint8 status) external {
    55  
    56          require(admin.account == msg.sender);
    57  
    58          require(status == 0 || status == 1 || status == 2 || status == 3);
    59  
    60          if (admin.status != status) {
    61  
    62              admin.status = status;
    63          }
    64      }
    65  
    66      function getStatus() external view returns (uint8) {
    67  
    68          return admin.status;
    69      }
    70  
    71      function setPlatformName(bytes32 platformName) external {
    72  
    73          require(admin.account == msg.sender);
    74  
    75          if (admin.platformName != platformName) {
    76  
    77              admin.platformName = platformName;
    78          }
    79      }
    80  
    81      function getPlatformName() external view returns (bytes32) {
    82  
    83          return admin.platformName;
    84      }
    85  
    86      function setAdmin(address account) external {
    87  
    88          require(account != address(0));
    89  
    90          require(admin.account == msg.sender);
    91  
    92          if (admin.account != account) {
    93  
    94              admin.account = account;
    95          }
    96      }
    97  
    98      function getAdmin() external view returns (address) {
    99  
   100          return admin.account;
   101      }
   102  
   103      function setToken(address account) external {
   104  
   105          require(admin.account == msg.sender);
   106  
   107          if (token != account) {
   108  
   109              token = Token(account);
   110          }
   111      }
   112  
   113      function getToken() external view returns (address) {
   114  
   115          return token;
   116      }
   117  
   118      function setXCPlugin(address account) external {
   119  
   120          require(admin.account == msg.sender);
   121  
   122          if (xcPlugin != account) {
   123  
   124              xcPlugin = XCPlugin(account);
   125          }
   126      }
   127  
   128      function getXCPlugin() external view returns (address) {
   129  
   130          return xcPlugin;
   131      }
   132  
   133      function setCompare(bytes2 symbol) external {
   134  
   135          require(admin.account == msg.sender);
   136  
   137          require(symbol == "+=" || symbol == "-=");
   138  
   139          if (compareSymbol != symbol) {
   140  
   141              compareSymbol = symbol;
   142          }
   143      }
   144  
   145      function getCompare() external view returns (bytes2){
   146  
   147          require(admin.account == msg.sender);
   148  
   149          return compareSymbol;
   150      }
   151  
   152      function lock(bytes32 toPlatform, address toAccount, uint value) external payable {
   153  
   154          require(admin.status == 2 || admin.status == 3);
   155  
   156          require(xcPlugin.getStatus());
   157  
   158          require(xcPlugin.existPlatform(toPlatform));
   159  
   160          require(toAccount != address(0));
   161  
   162          // require(uint(token.totalSupply) >= value && value > 0);
   163          require(value > 0);
   164  
   165          //get user approve the contract quota
   166          uint allowance = token.allowance(msg.sender, this);
   167  
   168          require(toCompare(allowance, value));
   169  
   170          //do transferFrom
   171          bool success = token.transferFrom(msg.sender, this, value);
   172  
   173          require(success);
   174  
   175          //record the amount of local platform turn out
   176          lockBalance = SafeMath.add(lockBalance, value);
   177          // require(token.totalSupply >= lockBalance);
   178  
   179          //trigger lockEvent
   180          emit Lock(toPlatform, toAccount, uintAppendToString(value));
   181      }
   182  
   183      //turn in
   184      function unlock(string txid, bytes32 fromPlatform, address fromAccount, address toAccount, uint value) external payable {
   185  
   186          require(admin.status == 1 || admin.status == 3);
   187  
   188          require(xcPlugin.getStatus());
   189  
   190          require(xcPlugin.existPlatform(fromPlatform));
   191  
   192          require(toAccount != address(0));
   193  
   194          // require(token.totalSupply >= value && value > 0);
   195          require(value > 0);
   196  
   197          bool complete;
   198  
   199          bool verify;
   200  
   201          //verify args by function xcPlugin.verify
   202          (complete, verify) = xcPlugin.verifyProposal(fromPlatform, fromAccount, toAccount, value, txid);
   203  
   204          require(verify && !complete);
   205  
   206          //get contracts balance
   207          uint balance = token.balanceOf(this);
   208  
   209          //validate the balance of contract were less than amount
   210          require(toCompare(balance, value));
   211  
   212          // require(token.transfer(toAccount, value));
   213          token.transfer(toAccount, value);
   214  
   215          require(xcPlugin.commitProposal(fromPlatform, txid));
   216  
   217          lockBalance = SafeMath.sub(lockBalance, value);
   218  
   219          emit Unlock(txid, fromPlatform, fromAccount, uintAppendToString(value));
   220      }
   221  
   222      function withdraw(address account, uint value) external payable {
   223  
   224          require(admin.account == msg.sender);
   225  
   226          require(account != address(0));
   227  
   228          require(value > 0);
   229          // require(token.totalSupply >= value && value > 0);
   230  
   231          uint balance = token.balanceOf(this);
   232  
   233          require(toCompare(SafeMath.sub(balance, lockBalance), value));
   234  
   235          token.transfer(account, value);
   236      }
   237  
   238      function transfer(address account, uint value) external payable {
   239  
   240          require(admin.account == msg.sender);
   241  
   242          require(account != address(0));
   243  
   244          require(value > 0 && value >= this.balance);
   245  
   246          this.transfer(account, value);
   247      }
   248  
   249      /**
   250       *   ######################
   251       *  #  private function  #
   252       * ######################
   253       */
   254  
   255      function toCompare(uint f, uint s) internal view returns (bool) {
   256  
   257          if (compareSymbol == "-=") {
   258  
   259              return f > s;
   260          } else if (compareSymbol == "+=") {
   261  
   262              return f >= s;
   263          } else {
   264  
   265              return false;
   266          }
   267      }
   268  
   269      function uintAppendToString(uint v) pure internal returns (string){
   270  
   271          uint length = 100;
   272  
   273          bytes memory reversed = new bytes(length);
   274  
   275          bytes16 sixTeenStr = "0123456789abcdef";
   276  
   277          uint i = 0;
   278  
   279          while (v != 0) {
   280  
   281              uint remainder = v % 16;
   282  
   283              v = v / 16;
   284  
   285              reversed[i++] = byte(sixTeenStr[remainder]);
   286          }
   287  
   288          string memory bytesList = "0000000000000000000000000000000000000000000000000000000000000000";
   289  
   290          bytes memory str = bytes(bytesList);
   291  
   292          for (uint j = 0; j < i; j++) {
   293  
   294              str[str.length - j - 1] = reversed[i - j - 1];
   295          }
   296  
   297          return string(str);
   298      }
   299  }