From ba648bc4aa0cb2ac3985dc0c37e11cd11757b0fd Mon Sep 17 00:00:00 2001
From: Jeremy Rubin <j@rubin.io>
Date: Tue, 29 Mar 2022 14:51:43 -0700
Subject: Update BIP-119 to include python reference hash / link BIP-341

---
 bip-0119.mediawiki | 28 +++++++++++++++++++++++++++-
 1 file changed, 27 insertions(+), 1 deletion(-)

(limited to 'bip-0119.mediawiki')

diff --git a/bip-0119.mediawiki b/bip-0119.mediawiki
index 96df4d9..07ce53a 100644
--- a/bip-0119.mediawiki
+++ b/bip-0119.mediawiki
@@ -203,7 +203,18 @@ Where
         return GetDefaultCheckTemplateVerifyHash(current_tx, current_input_index) == uint256(hash);
     }
 
-The hash is computed as follows:
+The hash is computed as follows, where the outputs_hash and sequences_hash are computed as defined in BIP-341.
+
+    /** Compute the (single) SHA256 of the concatenation of all scriptSigs in a tx. */
+    template <class T>
+    uint256 GetScriptSigsSHA256(const T& txTo)
+    {
+        CHashWriter ss(SER_GETHASH, 0);
+        for (const auto& in : txTo.vin) {
+            ss << in.scriptSig;
+        }
+        return ss.GetSHA256();
+    }
     // not DoS safe, for reference/testing!
     uint256 GetDefaultCheckTemplateVerifyHash(const CTransaction& tx, uint32_t input_index) {
         return GetDefaultCheckTemplateVerifyHash(tx, GetOutputsSHA256(tx), GetSequenceSHA256(tx), input_index);
@@ -244,6 +255,21 @@ The hash is computed as follows:
         return h.GetSHA256();
     }
 
+In python, this can be written as (but note this implementation is DoS-able).
+
+    def get_default_check_template_hash(self, nIn):
+        r = b""
+        r += struct.pack("<i", self.nVersion)
+        r += struct.pack("<I", self.nLockTime)
+        if any(inp.scriptSig for inp in self.vin):
+            r += sha256(b"".join(ser_string(inp.scriptSig) for inp in self.vin))
+        r += struct.pack("<I", len(self.vin))
+        r += sha256(b"".join(struct.pack("<I", inp.nSequence) for inp in self.vin))
+        r += struct.pack("<I", len(self.vout))
+        r += sha256(b"".join(out.serialize() for out in self.vout))
+        r += struct.pack("<I", nIn)
+        return sha256(r)
+
 A PayToBareDefaultCheckTemplateVerifyHash output matches the following template:
 
     bool CScript::IsPayToBareDefaultCheckTemplateVerifyHash() const
-- 
cgit v1.2.3

