/**
* Novacoin classes library
* Copyright (C) 2015 Alex D. (balthazar.ad@gmail.com)
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License as
* published by the Free Software Foundation, either version 3 of the
* License, or (at your option) any later version.
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
* You should have received a copy of the GNU Affero General Public License
* along with this program. If not, see .
*/
using System;
using System.Text;
using System.Collections.Generic;
namespace Novacoin
{
[Serializable]
public class TxInConstructorException : Exception
{
public TxInConstructorException()
{
}
public TxInConstructorException(string message)
: base(message)
{
}
public TxInConstructorException(string message, Exception inner)
: base(message, inner)
{
}
}
///
/// Transaction input.
///
public class CTxIn
{
///
/// Previous input data
///
public COutPoint prevout;
///
/// First half of script, signatures for the scriptPubKey
///
public CScript scriptSig;
///
/// Transaction variant number, irrelevant if nLockTime isn't specified. Its value is 0xffffffff by default.
///
public uint nSequence = uint.MaxValue;
///
/// Initialize new CTxIn instance as copy of another one.
///
/// CTxIn instance.
public CTxIn(CTxIn i)
{
prevout = new COutPoint(i.prevout);
scriptSig = i.scriptSig;
nSequence = i.nSequence;
}
///
/// Initialize an empty instance of CTxIn class
///
public CTxIn()
{
prevout = new COutPoint();
scriptSig = new CScript();
}
///
/// Read vin list from byte sequence.
///
/// Reference to byte sequence
/// Inputs array
public static CTxIn[] ReadTxInList(ref ByteQueue wBytes)
{
try
{
// Get amount
int nInputs = (int)wBytes.GetVarInt();
var vin = new CTxIn[nInputs];
for (int nIndex = 0; nIndex < nInputs; nIndex++)
{
// Fill inputs array
vin[nIndex] = new CTxIn();
vin[nIndex].prevout = new COutPoint(wBytes.Get(36));
vin[nIndex].scriptSig = new CScript(wBytes.Get((int)wBytes.GetVarInt()));
vin[nIndex].nSequence = BitConverter.ToUInt32(wBytes.Get(4), 0);
}
// Return inputs array
return vin;
}
catch (Exception e)
{
throw new TxInConstructorException("Desirealization failed.", e);
}
}
///
/// Serialized size
///
public int Size
{
get {
int nSize = 40; // COutPoint, nSequence
nSize += VarInt.GetEncodedSize(scriptSig.Size);
nSize += scriptSig.Size;
return nSize;
}
}
///
/// Get raw bytes representation of our input.
///
/// Byte sequence.
public static implicit operator byte[] (CTxIn input)
{
var inputBytes = new List();
inputBytes.AddRange((byte[])input.prevout); // prevout
var s = (byte[])input.scriptSig;
inputBytes.AddRange(VarInt.EncodeVarInt(s.Length)); // scriptSig length
inputBytes.AddRange(s); // scriptSig
inputBytes.AddRange(BitConverter.GetBytes(input.nSequence)); // Sequence
return inputBytes.ToArray();
}
public bool IsFinal
{
get { return (nSequence == uint.MaxValue); }
}
public override string ToString ()
{
StringBuilder sb = new StringBuilder ();
sb.AppendFormat("CTxIn(");
sb.Append(prevout.ToString());
if(prevout.IsNull)
{
sb.AppendFormat(", coinbase={0}", Interop.ToHex((byte[])scriptSig));
}
else
{
sb.AppendFormat(", scriptsig={0}", scriptSig.ToString());
}
if (nSequence != uint.MaxValue)
{
sb.AppendFormat(", nSequence={0}", nSequence);
}
sb.Append(")");
return sb.ToString ();
}
}
}