Init some fields, add ToString() for Hash160 and Hash256, start implementation of...
authorCryptoManiac <balthazar@yandex.ru>
Thu, 6 Aug 2015 10:28:21 +0000 (13:28 +0300)
committerCryptoManiac <balthazar@yandex.ru>
Thu, 6 Aug 2015 10:28:21 +0000 (13:28 +0300)
Novacoin/CBlock.cs
Novacoin/CBlockHeader.cs
Novacoin/CScript.cs [new file with mode: 0644]
Novacoin/CTransaction.cs
Novacoin/CTxIn.cs
Novacoin/CTxOut.cs
Novacoin/Hash160.cs
Novacoin/Hash256.cs
Novacoin/Novacoin.csproj

index a794846..4eb3a33 100644 (file)
@@ -20,7 +20,7 @@ namespace Novacoin
                /// <summary>
                /// Block header signature.
                /// </summary>
-               public byte[] signature;
+               public byte[] signature = {};
 
                public CBlock ()
                {
index 0ccc1fb..de9f449 100644 (file)
@@ -2,41 +2,43 @@
 
 namespace Novacoin
 {
+       /// <summary>
+       /// Block header
+       /// </summary>
        public class CBlockHeader
        {
                /// <summary>
                /// Version of block schema.
                /// </summary>
-               public uint nVersion;
+               public uint nVersion = 6;
 
                /// <summary>
                /// Previous block hash.
                /// </summary>
-               public Hash256 prevHash;
+               public Hash256 prevHash = new Hash256();
 
                /// <summary>
                /// Merkle root hash.
                /// </summary>
-               public Hash256 merkleRoot;
+               public Hash256 merkleRoot = new Hash256();
 
                /// <summary>
                /// Block timestamp.
                /// </summary>
-               public uint nTime;
+               public uint nTime = 0;
 
                /// <summary>
                /// Compressed difficulty representation.
                /// </summary>
-               public uint nBits;
+               public uint nBits = 0;
 
                /// <summary>
                /// Nonce counter.
                /// </summary>
-               public uint nNonce;
+               public uint nNonce = 0;
 
                public CBlockHeader ()
                {
                }
        }
 }
-
diff --git a/Novacoin/CScript.cs b/Novacoin/CScript.cs
new file mode 100644 (file)
index 0000000..70cf412
--- /dev/null
@@ -0,0 +1,429 @@
+\feffusing System;
+using System.Text;
+
+namespace Novacoin
+{
+       /** Script opcodes */
+       enum opcodetype
+       {
+               // push value
+               OP_0 = 0x00,
+               OP_FALSE = OP_0,
+               OP_PUSHDATA1 = 0x4c,
+               OP_PUSHDATA2 = 0x4d,
+               OP_PUSHDATA4 = 0x4e,
+               OP_1NEGATE = 0x4f,
+               OP_RESERVED = 0x50,
+               OP_1 = 0x51,
+               OP_TRUE=OP_1,
+               OP_2 = 0x52,
+               OP_3 = 0x53,
+               OP_4 = 0x54,
+               OP_5 = 0x55,
+               OP_6 = 0x56,
+               OP_7 = 0x57,
+               OP_8 = 0x58,
+               OP_9 = 0x59,
+               OP_10 = 0x5a,
+               OP_11 = 0x5b,
+               OP_12 = 0x5c,
+               OP_13 = 0x5d,
+               OP_14 = 0x5e,
+               OP_15 = 0x5f,
+               OP_16 = 0x60,
+
+               // control
+               OP_NOP = 0x61,
+               OP_VER = 0x62,
+               OP_IF = 0x63,
+               OP_NOTIF = 0x64,
+               OP_VERIF = 0x65,
+               OP_VERNOTIF = 0x66,
+               OP_ELSE = 0x67,
+               OP_ENDIF = 0x68,
+               OP_VERIFY = 0x69,
+               OP_RETURN = 0x6a,
+
+               // stack ops
+               OP_TOALTSTACK = 0x6b,
+               OP_FROMALTSTACK = 0x6c,
+               OP_2DROP = 0x6d,
+               OP_2DUP = 0x6e,
+               OP_3DUP = 0x6f,
+               OP_2OVER = 0x70,
+               OP_2ROT = 0x71,
+               OP_2SWAP = 0x72,
+               OP_IFDUP = 0x73,
+               OP_DEPTH = 0x74,
+               OP_DROP = 0x75,
+               OP_DUP = 0x76,
+               OP_NIP = 0x77,
+               OP_OVER = 0x78,
+               OP_PICK = 0x79,
+               OP_ROLL = 0x7a,
+               OP_ROT = 0x7b,
+               OP_SWAP = 0x7c,
+               OP_TUCK = 0x7d,
+
+               // splice ops
+               OP_CAT = 0x7e,
+               OP_SUBSTR = 0x7f,
+               OP_LEFT = 0x80,
+               OP_RIGHT = 0x81,
+               OP_SIZE = 0x82,
+
+               // bit logic
+               OP_INVERT = 0x83,
+               OP_AND = 0x84,
+               OP_OR = 0x85,
+               OP_XOR = 0x86,
+               OP_EQUAL = 0x87,
+               OP_EQUALVERIFY = 0x88,
+               OP_RESERVED1 = 0x89,
+               OP_RESERVED2 = 0x8a,
+
+               // numeric
+               OP_1ADD = 0x8b,
+               OP_1SUB = 0x8c,
+               OP_2MUL = 0x8d,
+               OP_2DIV = 0x8e,
+               OP_NEGATE = 0x8f,
+               OP_ABS = 0x90,
+               OP_NOT = 0x91,
+               OP_0NOTEQUAL = 0x92,
+
+               OP_ADD = 0x93,
+               OP_SUB = 0x94,
+               OP_MUL = 0x95,
+               OP_DIV = 0x96,
+               OP_MOD = 0x97,
+               OP_LSHIFT = 0x98,
+               OP_RSHIFT = 0x99,
+
+               OP_BOOLAND = 0x9a,
+               OP_BOOLOR = 0x9b,
+               OP_NUMEQUAL = 0x9c,
+               OP_NUMEQUALVERIFY = 0x9d,
+               OP_NUMNOTEQUAL = 0x9e,
+               OP_LESSTHAN = 0x9f,
+               OP_GREATERTHAN = 0xa0,
+               OP_LESSTHANOREQUAL = 0xa1,
+               OP_GREATERTHANOREQUAL = 0xa2,
+               OP_MIN = 0xa3,
+               OP_MAX = 0xa4,
+
+               OP_WITHIN = 0xa5,
+
+               // crypto
+               OP_RIPEMD160 = 0xa6,
+               OP_SHA1 = 0xa7,
+               OP_SHA256 = 0xa8,
+               OP_HASH160 = 0xa9,
+               OP_HASH256 = 0xaa,
+               OP_CODESEPARATOR = 0xab,
+               OP_CHECKSIG = 0xac,
+               OP_CHECKSIGVERIFY = 0xad,
+               OP_CHECKMULTISIG = 0xae,
+               OP_CHECKMULTISIGVERIFY = 0xaf,
+
+               // expansion
+               OP_NOP1 = 0xb0,
+               OP_NOP2 = 0xb1,
+               OP_NOP3 = 0xb2,
+               OP_NOP4 = 0xb3,
+               OP_NOP5 = 0xb4,
+               OP_NOP6 = 0xb5,
+               OP_NOP7 = 0xb6,
+               OP_NOP8 = 0xb7,
+               OP_NOP9 = 0xb8,
+               OP_NOP10 = 0xb9,
+
+
+               // template matching params
+               OP_SMALLDATA = 0xf9,
+               OP_SMALLINTEGER = 0xfa,
+               OP_PUBKEYS = 0xfb,
+               OP_PUBKEYHASH = 0xfd,
+               OP_PUBKEY = 0xfe,
+
+               OP_INVALIDOPCODE = 0xff,
+       };
+
+       public class CScript
+       {
+               private byte[] scriptCode = {};
+
+               public CScript ()
+               {
+               }
+
+               private string GetOpName(opcodetype opcode)
+               {
+                       switch (opcode) {
+                       // push value
+                       case opcodetype.OP_0:
+                               return "0";
+                       case opcodetype.OP_PUSHDATA1:
+                               return "OP_PUSHDATA1";
+                       case opcodetype.OP_PUSHDATA2:
+                               return "OP_PUSHDATA2";
+                       case opcodetype.OP_PUSHDATA4:
+                               return "OP_PUSHDATA4";
+                       case opcodetype.OP_1NEGATE:
+                               return "-1";
+                       case opcodetype.OP_RESERVED:
+                               return "OP_RESERVED";
+                       case opcodetype.OP_1:
+                               return "1";
+                       case opcodetype.OP_2:
+                               return "2";
+                       case opcodetype.OP_3:
+                               return "3";
+                       case opcodetype.OP_4:
+                               return "4";
+                       case opcodetype.OP_5:
+                               return "5";
+                       case opcodetype.OP_6:
+                               return "6";
+                       case opcodetype.OP_7:
+                               return "7";
+                       case opcodetype.OP_8:
+                               return "8";
+                       case opcodetype.OP_9:
+                               return "9";
+                       case opcodetype.OP_10:
+                               return "10";
+                       case opcodetype.OP_11:
+                               return "11";
+                       case opcodetype.OP_12:
+                               return "12";
+                       case opcodetype.OP_13:
+                               return "13";
+                       case opcodetype.OP_14:
+                               return "14";
+                       case opcodetype.OP_15:
+                               return "15";
+                       case opcodetype.OP_16:
+                               return "16";
+
+                       // control
+                       case opcodetype.OP_NOP:
+                               return "OP_NOP";
+                       case opcodetype.OP_VER:
+                               return "OP_VER";
+                       case opcodetype.OP_IF:
+                               return "OP_IF";
+                       case opcodetype.OP_NOTIF:
+                               return "OP_NOTIF";
+                       case opcodetype.OP_VERIF:
+                               return "OP_VERIF";
+                       case opcodetype.OP_VERNOTIF:
+                               return "OP_VERNOTIF";
+                       case opcodetype.OP_ELSE:
+                               return "OP_ELSE";
+                       case opcodetype.OP_ENDIF:
+                               return "OP_ENDIF";
+                       case opcodetype.OP_VERIFY:
+                               return "OP_VERIFY";
+                       case opcodetype.OP_RETURN:
+                               return "OP_RETURN";
+
+                       // stack ops
+                       case opcodetype.OP_TOALTSTACK:
+                               return "OP_TOALTSTACK";
+                       case opcodetype.OP_FROMALTSTACK:
+                               return "OP_FROMALTSTACK";
+                       case opcodetype.OP_2DROP:
+                               return "OP_2DROP";
+                       case opcodetype.OP_2DUP:
+                               return "OP_2DUP";
+                       case opcodetype.OP_3DUP:
+                               return "OP_3DUP";
+                       case opcodetype.OP_2OVER:
+                               return "OP_2OVER";
+                       case opcodetype.OP_2ROT:
+                               return "OP_2ROT";
+                       case opcodetype.OP_2SWAP:
+                               return "OP_2SWAP";
+                       case opcodetype.OP_IFDUP:
+                               return "OP_IFDUP";
+                       case opcodetype.OP_DEPTH:
+                               return "OP_DEPTH";
+                       case opcodetype.OP_DROP:
+                               return "OP_DROP";
+                       case opcodetype.OP_DUP:
+                               return "OP_DUP";
+                       case opcodetype.OP_NIP:
+                               return "OP_NIP";
+                       case opcodetype.OP_OVER:
+                               return "OP_OVER";
+                       case opcodetype.OP_PICK:
+                               return "OP_PICK";
+                       case opcodetype.OP_ROLL:
+                               return "OP_ROLL";
+                       case opcodetype.OP_ROT:
+                               return "OP_ROT";
+                       case opcodetype.OP_SWAP:
+                               return "OP_SWAP";
+                       case opcodetype.OP_TUCK:
+                               return "OP_TUCK";
+
+                       // splice ops
+                       case opcodetype.OP_CAT:
+                               return "OP_CAT";
+                       case opcodetype.OP_SUBSTR:
+                               return "OP_SUBSTR";
+                       case opcodetype.OP_LEFT:
+                               return "OP_LEFT";
+                       case opcodetype.OP_RIGHT:
+                               return "OP_RIGHT";
+                       case opcodetype.OP_SIZE:
+                               return "OP_SIZE";
+
+                       // bit logic
+                       case opcodetype.OP_INVERT:
+                               return "OP_INVERT";
+                       case opcodetype.OP_AND:
+                               return "OP_AND";
+                       case opcodetype.OP_OR:
+                               return "OP_OR";
+                       case opcodetype.OP_XOR:
+                               return "OP_XOR";
+                       case opcodetype.OP_EQUAL:
+                               return "OP_EQUAL";
+                       case opcodetype.OP_EQUALVERIFY:
+                               return "OP_EQUALVERIFY";
+                       case opcodetype.OP_RESERVED1:
+                               return "OP_RESERVED1";
+                       case opcodetype.OP_RESERVED2:
+                               return "OP_RESERVED2";
+
+                       // numeric
+                       case opcodetype.OP_1ADD:
+                               return "OP_1ADD";
+                       case opcodetype.OP_1SUB:
+                               return "OP_1SUB";
+                       case opcodetype.OP_2MUL:
+                               return "OP_2MUL";
+                       case opcodetype.OP_2DIV:
+                               return "OP_2DIV";
+                       case opcodetype.OP_NEGATE:
+                               return "OP_NEGATE";
+                       case opcodetype.OP_ABS:
+                               return "OP_ABS";
+                       case opcodetype.OP_NOT:
+                               return "OP_NOT";
+                       case opcodetype.OP_0NOTEQUAL:
+                               return "OP_0NOTEQUAL";
+                       case opcodetype.OP_ADD:
+                               return "OP_ADD";
+                       case opcodetype.OP_SUB:
+                               return "OP_SUB";
+                       case opcodetype.OP_MUL:
+                               return "OP_MUL";
+                       case opcodetype.OP_DIV:
+                               return "OP_DIV";
+                       case opcodetype.OP_MOD:
+                               return "OP_MOD";
+                       case opcodetype.OP_LSHIFT:
+                               return "OP_LSHIFT";
+                       case opcodetype.OP_RSHIFT:
+                               return "OP_RSHIFT";
+                       case opcodetype.OP_BOOLAND:
+                               return "OP_BOOLAND";
+                       case opcodetype.OP_BOOLOR:
+                               return "OP_BOOLOR";
+                       case opcodetype.OP_NUMEQUAL:
+                               return "OP_NUMEQUAL";
+                       case opcodetype.OP_NUMEQUALVERIFY:
+                               return "OP_NUMEQUALVERIFY";
+                       case opcodetype.OP_NUMNOTEQUAL:
+                               return "OP_NUMNOTEQUAL";
+                       case opcodetype.OP_LESSTHAN:
+                               return "OP_LESSTHAN";
+                       case opcodetype.OP_GREATERTHAN:
+                               return "OP_GREATERTHAN";
+                       case opcodetype.OP_LESSTHANOREQUAL:
+                               return "OP_LESSTHANOREQUAL";
+                       case opcodetype.OP_GREATERTHANOREQUAL:
+                               return "OP_GREATERTHANOREQUAL";
+                       case opcodetype.OP_MIN:
+                               return "OP_MIN";
+                       case opcodetype.OP_MAX:
+                               return "OP_MAX";
+                       case opcodetype.OP_WITHIN:
+                               return "OP_WITHIN";
+
+                       // crypto
+                       case opcodetype.OP_RIPEMD160:
+                               return "OP_RIPEMD160";
+                       case opcodetype.OP_SHA1:
+                               return "OP_SHA1";
+                       case opcodetype.OP_SHA256:
+                               return "OP_SHA256";
+                       case opcodetype.OP_HASH160:
+                               return "OP_HASH160";
+                       case opcodetype.OP_HASH256:
+                               return "OP_HASH256";
+                       case opcodetype.OP_CODESEPARATOR:
+                               return "OP_CODESEPARATOR";
+                       case opcodetype.OP_CHECKSIG:
+                               return "OP_CHECKSIG";
+                       case opcodetype.OP_CHECKSIGVERIFY:
+                               return "OP_CHECKSIGVERIFY";
+                       case opcodetype.OP_CHECKMULTISIG:
+                               return "OP_CHECKMULTISIG";
+                       case opcodetype.OP_CHECKMULTISIGVERIFY:
+                               return "OP_CHECKMULTISIGVERIFY";
+
+                       // expanson
+                       case opcodetype.OP_NOP1:
+                               return "OP_NOP1";
+                       case opcodetype.OP_NOP2:
+                               return "OP_NOP2";
+                       case opcodetype.OP_NOP3:
+                               return "OP_NOP3";
+                       case opcodetype.OP_NOP4:
+                               return "OP_NOP4";
+                       case opcodetype.OP_NOP5:
+                               return "OP_NOP5";
+                       case opcodetype.OP_NOP6:
+                               return "OP_NOP6";
+                       case opcodetype.OP_NOP7:
+                               return "OP_NOP7";
+                       case opcodetype.OP_NOP8:
+                               return "OP_NOP8";
+                       case opcodetype.OP_NOP9:
+                               return "OP_NOP9";
+                       case opcodetype.OP_NOP10:
+                               return "OP_NOP10";
+
+                       // template matching params
+                       case opcodetype.OP_PUBKEYHASH:
+                               return "OP_PUBKEYHASH";
+                       case opcodetype.OP_PUBKEY:
+                               return "OP_PUBKEY";
+                       case opcodetype.OP_SMALLDATA:
+                               return "OP_SMALLDATA";
+
+                       case opcodetype.OP_INVALIDOPCODE:
+                               return "OP_INVALIDOPCODE";
+                       default:
+                               return "OP_UNKNOWN";
+                       }
+               }
+
+               public override string ToString()
+               {
+                       // TODO: disassembly 
+
+                       StringBuilder sb = new StringBuilder(scriptCode.Length * 2);
+                       foreach (byte b in scriptCode)
+                       {
+                               sb.AppendFormat ("{0:x2}", b);
+                       }
+                       return sb.ToString();
+               }
+       }
+}
+
index 29de940..422c849 100644 (file)
@@ -10,12 +10,12 @@ namespace Novacoin
                /// <summary>
                /// Version of transaction schema.
                /// </summary>
-               public uint nVersion;
+               public uint nVersion = 1;
 
                /// <summary>
                /// Transaction timestamp.
                /// </summary>
-               public uint nTime;
+               public uint nTime = 0;
 
                /// <summary>
                /// Array of transaction inputs
@@ -30,7 +30,7 @@ namespace Novacoin
                /// <summary>
                /// Block height or timestamp when transaction is final
                /// </summary>
-               public uint nLockTime;
+               public uint nLockTime = 0;
 
                public CTransaction ()
                {
index 6c4b5ec..4e6c615 100644 (file)
@@ -1,18 +1,22 @@
 \feffusing System;
+using System.Text;
 
 namespace Novacoin
 {
+       /// <summary>
+       /// Transaction input.
+       /// </summary>
        public class CTxIn
        {
                /// <summary>
                /// Hash of parent transaction.
                /// </summary>
-               public Hash256 txID;
+               public Hash256 txID = new Hash256();
 
                /// <summary>
                /// Parent input number.
                /// </summary>
-               public uint nInput;
+               public uint nInput = 0;
 
                /// <summary>
                /// First half of script, signatures for the scriptPubKey
@@ -22,11 +26,20 @@ namespace Novacoin
                /// <summary>
                /// Transaction variant number, irrelevant if nLockTime isn't specified. Its value is 0xffffffff by default.
                /// </summary>
-               public uint nSequence;
+               public uint nSequence = 0xffffffff;
 
                public CTxIn ()
                {
                }
+
+               public override string ToString ()
+               {
+                       StringBuilder sb = new StringBuilder ();
+                       sb.AppendFormat ("CTxIn(txId={0},n={1},scriptSig={2}", nInput, nInput, scriptSig.ToString());
+
+                       return sb.ToString ();
+               }
+
        }
 }
 
index 2dc5344..8ac5c7c 100644 (file)
@@ -1,4 +1,5 @@
 \feffusing System;
+using System.Text;
 
 namespace Novacoin
 {
@@ -10,7 +11,7 @@ namespace Novacoin
                /// <summary>
                /// Input value.
                /// </summary>
-               public ulong nValue;
+               public ulong nValue = 0;
 
                /// <summary>
                /// Second half of script which contains spending instructions.
@@ -20,6 +21,14 @@ namespace Novacoin
                public CTxOut ()
                {
                }
+
+               public override string ToString ()
+               {
+                       StringBuilder sb = new StringBuilder ();
+                       sb.AppendFormat ("CTxOut(nValue={0},scriptPubKey={1}", nValue, scriptPubKey.ToString());
+
+                       return sb.ToString ();
+               }
        }
 }
 
index 8a995d5..993e4c9 100644 (file)
@@ -1,4 +1,6 @@
 \feffusing System;
+using System.Text;
+using System.Linq;
 
 namespace Novacoin
 {
@@ -12,9 +14,25 @@ namespace Novacoin
                /// </summary>
                private byte[] h;
 
+               /// <summary>
+               /// Initializes an empty instance of the Hash160 class.
+               /// </summary>
                public Hash160 ()
                {
+                       // Fill with 20 zero bytes
+                       h = Enumerable.Repeat<byte> (0, 20).ToArray ();
+               }
+
+               public override string ToString()
+               {
+                       StringBuilder sb = new StringBuilder(h.Length * 2);
+                       foreach (byte b in h)
+                       {
+                               sb.AppendFormat ("{0:x2}", b);
+                       }
+                       return sb.ToString();
                }
+
        }
 }
 
index 655b300..365f778 100644 (file)
@@ -1,4 +1,6 @@
 \feffusing System;
+using System.Text;
+using System.Linq;
 
 namespace Novacoin
 {
@@ -12,8 +14,22 @@ namespace Novacoin
                /// </summary>
                private byte[] h;
 
+               /// <summary>
+               /// Initializes an empty instance of the Hash256 class.
+               /// </summary>
                public Hash256 ()
                {
+                       h = Enumerable.Repeat<byte>(0, 32).ToArray();
+               }
+
+               public override string ToString()
+               {
+                       StringBuilder sb = new StringBuilder(h.Length * 2);
+                       foreach (byte b in h)
+                       {
+                               sb.AppendFormat ("{0:x2}", b);
+                       }
+                       return sb.ToString();
                }
        }
 }
index 9f14b3c..9c9934b 100644 (file)
@@ -39,6 +39,7 @@
     <Compile Include="Hash160.cs" />
     <Compile Include="CBlockHeader.cs" />
     <Compile Include="CBlock.cs" />
+    <Compile Include="CScript.cs" />
   </ItemGroup>
   <Import Project="$(MSBuildBinPath)\Microsoft.CSharp.targets" />
 </Project>
\ No newline at end of file