-
Notifications
You must be signed in to change notification settings - Fork 110
/
marshal.go
154 lines (133 loc) · 3.87 KB
/
marshal.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
package taprpc
import (
"context"
"fmt"
"github.com/lightninglabs/taproot-assets/asset"
"github.com/lightningnetwork/lnd/keychain"
)
// KeyLookup is used to determine whether a key is under the control of the
// local wallet.
type KeyLookup interface {
// IsLocalKey returns true if the key is under the control of the
// wallet and can be derived by it.
IsLocalKey(ctx context.Context, desc keychain.KeyDescriptor) bool
}
// UnmarshalAssetVersion parses an asset version from the RPC variant.
func UnmarshalAssetVersion(version AssetVersion) (asset.Version, error) {
// For now we'll only support two asset versions. The ones in the
// future should be reserved for future use, so we disallow unknown
// versions.
switch version {
case AssetVersion_ASSET_VERSION_V0:
return asset.V0, nil
case AssetVersion_ASSET_VERSION_V1:
return asset.V1, nil
default:
return 0, fmt.Errorf("unknown asset version: %v", version)
}
}
// MarshalAssetVersion parses an asset version from the RPC variant.
func MarshalAssetVersion(version asset.Version) (AssetVersion, error) {
// For now we'll only support two asset versions. The ones in the
// future should be reserved for future use, so we disallow unknown
// versions.
switch version {
case asset.V0:
return AssetVersion_ASSET_VERSION_V0, nil
case asset.V1:
return AssetVersion_ASSET_VERSION_V1, nil
default:
return 0, fmt.Errorf("unknown asset version: %v", version)
}
}
// MarshalAsset converts an asset to its rpc representation.
func MarshalAsset(ctx context.Context, a *asset.Asset,
isSpent, withWitness bool,
keyRing KeyLookup) (*Asset, error) {
assetID := a.Genesis.ID()
scriptKeyIsLocal := false
if a.ScriptKey.TweakedScriptKey != nil && keyRing != nil {
scriptKeyIsLocal = keyRing.IsLocalKey(
ctx, a.ScriptKey.RawKey,
)
}
assetVersion, err := MarshalAssetVersion(a.Version)
if err != nil {
return nil, err
}
rpcAsset := &Asset{
Version: assetVersion,
AssetGenesis: &GenesisInfo{
GenesisPoint: a.Genesis.FirstPrevOut.String(),
AssetType: AssetType(a.Type),
Name: a.Genesis.Tag,
MetaHash: a.Genesis.MetaHash[:],
AssetId: assetID[:],
OutputIndex: a.Genesis.OutputIndex,
Version: int32(assetVersion),
},
Amount: a.Amount,
LockTime: int32(a.LockTime),
RelativeLockTime: int32(a.RelativeLockTime),
ScriptVersion: int32(a.ScriptVersion),
ScriptKey: a.ScriptKey.PubKey.SerializeCompressed(),
ScriptKeyIsLocal: scriptKeyIsLocal,
IsSpent: isSpent,
IsBurn: a.IsBurn(),
}
if a.GroupKey != nil {
var (
rawKey []byte
groupWitness []byte
err error
)
if a.GroupKey.RawKey.PubKey != nil {
rawKey = a.GroupKey.RawKey.PubKey.SerializeCompressed()
}
if len(a.GroupKey.Witness) != 0 {
groupWitness, err = asset.SerializeGroupWitness(
a.GroupKey.Witness,
)
if err != nil {
return nil, err
}
}
rpcAsset.AssetGroup = &AssetGroup{
RawGroupKey: rawKey,
TweakedGroupKey: a.GroupKey.GroupPubKey.SerializeCompressed(),
AssetWitness: groupWitness,
}
}
if withWitness {
for idx := range a.PrevWitnesses {
witness := a.PrevWitnesses[idx]
prevID := witness.PrevID
rpcPrevID := &PrevInputAsset{
AnchorPoint: prevID.OutPoint.String(),
AssetId: prevID.ID[:],
ScriptKey: prevID.ScriptKey[:],
}
var rpcSplitCommitment *SplitCommitment
if witness.SplitCommitment != nil {
rootAsset, err := MarshalAsset(
ctx, &witness.SplitCommitment.RootAsset,
false, true, nil,
)
if err != nil {
return nil, err
}
rpcSplitCommitment = &SplitCommitment{
RootAsset: rootAsset,
}
}
rpcAsset.PrevWitnesses = append(
rpcAsset.PrevWitnesses, &PrevWitness{
PrevId: rpcPrevID,
TxWitness: witness.TxWitness,
SplitCommitment: rpcSplitCommitment,
},
)
}
}
return rpcAsset, nil
}