Merge pull request #347 from spacebudz/constr
Fix constructor tag range
This commit is contained in:
		
						commit
						242eaa8b67
					
				|  | @ -8,7 +8,7 @@ use uplc::{ | ||||||
|         Constant as UplcConstant, Name, Term, Type as UplcType, |         Constant as UplcConstant, Name, Term, Type as UplcType, | ||||||
|     }, |     }, | ||||||
|     builtins::DefaultFunction, |     builtins::DefaultFunction, | ||||||
|     machine::runtime::convert_constr_to_tag, |     machine::runtime::{convert_constr_to_tag, ANY_TAG}, | ||||||
|     BigInt, Constr, KeyValuePairs, PlutusData, |     BigInt, Constr, KeyValuePairs, PlutusData, | ||||||
| }; | }; | ||||||
| 
 | 
 | ||||||
|  | @ -237,7 +237,7 @@ pub fn convert_type_to_data(term: Term<Name>, field_type: &Arc<Type>) -> Term<Na | ||||||
|             term, |             term, | ||||||
|             Term::Constant( |             Term::Constant( | ||||||
|                 UplcConstant::Data(PlutusData::Constr(Constr { |                 UplcConstant::Data(PlutusData::Constr(Constr { | ||||||
|                     tag: convert_constr_to_tag(1), |                     tag: convert_constr_to_tag(1).unwrap(), | ||||||
|                     any_constructor: None, |                     any_constructor: None, | ||||||
|                     fields: vec![], |                     fields: vec![], | ||||||
|                 })) |                 })) | ||||||
|  | @ -245,7 +245,7 @@ pub fn convert_type_to_data(term: Term<Name>, field_type: &Arc<Type>) -> Term<Na | ||||||
|             ), |             ), | ||||||
|             Term::Constant( |             Term::Constant( | ||||||
|                 UplcConstant::Data(PlutusData::Constr(Constr { |                 UplcConstant::Data(PlutusData::Constr(Constr { | ||||||
|                     tag: convert_constr_to_tag(0), |                     tag: convert_constr_to_tag(0).unwrap(), | ||||||
|                     any_constructor: None, |                     any_constructor: None, | ||||||
|                     fields: vec![], |                     fields: vec![], | ||||||
|                 })) |                 })) | ||||||
|  | @ -1002,8 +1002,9 @@ pub fn convert_constants_to_data(constants: Vec<Rc<UplcConstant>>) -> Vec<UplcCo | ||||||
|             )), |             )), | ||||||
| 
 | 
 | ||||||
|             UplcConstant::Bool(b) => UplcConstant::Data(PlutusData::Constr(Constr { |             UplcConstant::Bool(b) => UplcConstant::Data(PlutusData::Constr(Constr { | ||||||
|                 tag: convert_constr_to_tag((*b).into()), |                 tag: convert_constr_to_tag((*b).into()).unwrap_or(ANY_TAG), | ||||||
|                 any_constructor: None, |                 any_constructor: convert_constr_to_tag((*b).into()) | ||||||
|  |                     .map_or(Some((*b).into()), |_| None), | ||||||
|                 fields: vec![], |                 fields: vec![], | ||||||
|             })), |             })), | ||||||
|             UplcConstant::ProtoList(_, constants) => { |             UplcConstant::ProtoList(_, constants) => { | ||||||
|  |  | ||||||
|  | @ -880,9 +880,9 @@ impl DefaultFunction { | ||||||
|                                 .collect(); |                                 .collect(); | ||||||
| 
 | 
 | ||||||
|                             let constr_data = PlutusData::Constr(Constr { |                             let constr_data = PlutusData::Constr(Constr { | ||||||
|                                 // TODO: handle other types of constructor tags
 |                                 tag: convert_constr_to_tag(*i as u64).unwrap_or(ANY_TAG), | ||||||
|                                 tag: convert_constr_to_tag(*i as u64), |                                 any_constructor: convert_constr_to_tag(*i as u64) | ||||||
|                                 any_constructor: None, |                                     .map_or(Some(*i as u64), |_| None), | ||||||
|                                 fields: data_list, |                                 fields: data_list, | ||||||
|                             }); |                             }); | ||||||
| 
 | 
 | ||||||
|  | @ -959,27 +959,29 @@ impl DefaultFunction { | ||||||
|             }, |             }, | ||||||
|             DefaultFunction::UnConstrData => match args[0].as_ref() { |             DefaultFunction::UnConstrData => match args[0].as_ref() { | ||||||
|                 Value::Con(con) => match con.as_ref() { |                 Value::Con(con) => match con.as_ref() { | ||||||
|                     Constant::Data(PlutusData::Constr(c)) => { |                     Constant::Data(PlutusData::Constr(c)) => Ok(Value::Con( | ||||||
|                         Ok(Value::Con( |                         Constant::ProtoPair( | ||||||
|                             Constant::ProtoPair( |                             Type::Integer, | ||||||
|                                 Type::Integer, |                             Type::List(Type::Data.into()), | ||||||
|                                 Type::List(Type::Data.into()), |                             Constant::Integer( | ||||||
|                                 // TODO: handle other types of constructor tags
 |                                 convert_tag_to_constr(c.tag) | ||||||
|                                 Constant::Integer(convert_tag_to_constr(c.tag as i128)).into(), |                                     .unwrap_or_else(|| c.any_constructor.unwrap()) | ||||||
|                                 Constant::ProtoList( |                                     as i128, | ||||||
|                                     Type::Data, |                             ) | ||||||
|                                     c.fields |                             .into(), | ||||||
|                                         .deref() |                             Constant::ProtoList( | ||||||
|                                         .iter() |                                 Type::Data, | ||||||
|                                         .map(|d| Constant::Data(d.clone())) |                                 c.fields | ||||||
|                                         .collect(), |                                     .deref() | ||||||
|                                 ) |                                     .iter() | ||||||
|                                 .into(), |                                     .map(|d| Constant::Data(d.clone())) | ||||||
|  |                                     .collect(), | ||||||
|                             ) |                             ) | ||||||
|                             .into(), |                             .into(), | ||||||
|                         ) |                         ) | ||||||
|                         .into()) |                         .into(), | ||||||
|                     } |                     ) | ||||||
|  |                     .into()), | ||||||
|                     v => Err(Error::DeserialisationError( |                     v => Err(Error::DeserialisationError( | ||||||
|                         "UnConstrData".to_string(), |                         "UnConstrData".to_string(), | ||||||
|                         Value::Con(v.clone().into()), |                         Value::Con(v.clone().into()), | ||||||
|  | @ -1126,26 +1128,28 @@ impl DefaultFunction { | ||||||
|     } |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| pub fn convert_tag_to_constr(tag: i128) -> i128 { | pub fn convert_tag_to_constr(tag: u64) -> Option<u64> { | ||||||
|     if tag < 128 { |     if (121..=127).contains(&tag) { | ||||||
|         tag - 121 |         Some(tag - 121) | ||||||
|     } else if (1280..1401).contains(&tag) { |     } else if (1280..=1400).contains(&tag) { | ||||||
|         tag - 1280 |         Some(tag - 1280 + 7) | ||||||
|     } else { |     } else { | ||||||
|         todo!() |         None | ||||||
|     } |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| pub fn convert_constr_to_tag(constr: u64) -> u64 { | pub fn convert_constr_to_tag(constr: u64) -> Option<u64> { | ||||||
|     if constr < 7 { |     if (0..=6).contains(&constr) { | ||||||
|         constr + 121 |         Some(121 + constr) | ||||||
|     } else if constr < 128 { |     } else if (7..=127).contains(&constr) { | ||||||
|         constr + 1280 |         Some(1280 - 7 + constr) | ||||||
|     } else { |     } else { | ||||||
|         todo!() |         None // 102 otherwise
 | ||||||
|     } |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | pub static ANY_TAG: u64 = 102; | ||||||
|  | 
 | ||||||
| #[cfg(not(feature = "native-secp256k1"))] | #[cfg(not(feature = "native-secp256k1"))] | ||||||
| fn verify_ecdsa(public_key: &[u8], message: &[u8], signature: &[u8]) -> Result<Rc<Value>, Error> { | fn verify_ecdsa(public_key: &[u8], message: &[u8], signature: &[u8]) -> Result<Rc<Value>, Error> { | ||||||
|     use secp256k1::{ecdsa::Signature, Message, PublicKey, Secp256k1}; |     use secp256k1::{ecdsa::Signature, Message, PublicKey, Secp256k1}; | ||||||
|  |  | ||||||
|  | @ -8,37 +8,37 @@ use pallas_primitives::babbage::{ | ||||||
| }; | }; | ||||||
| use pallas_traverse::ComputeHash; | use pallas_traverse::ComputeHash; | ||||||
| 
 | 
 | ||||||
|  | use crate::machine::runtime::{convert_constr_to_tag, ANY_TAG}; | ||||||
|  | 
 | ||||||
| use super::script_context::{ScriptContext, ScriptPurpose, TimeRange, TxInInfo, TxInfo, TxOut}; | use super::script_context::{ScriptContext, ScriptPurpose, TimeRange, TxInInfo, TxInfo, TxOut}; | ||||||
| 
 | 
 | ||||||
| fn wrap_with_constr(index: u64, data: PlutusData) -> PlutusData { | fn wrap_with_constr(index: u64, data: PlutusData) -> PlutusData { | ||||||
|  |     let converted = convert_constr_to_tag(index); | ||||||
|     PlutusData::Constr(Constr { |     PlutusData::Constr(Constr { | ||||||
|         tag: constr_index(index), |         tag: converted.unwrap_or(ANY_TAG), | ||||||
|         any_constructor: None, |         any_constructor: converted.map_or(Some(index), |_| None), | ||||||
|         fields: vec![data], |         fields: vec![data], | ||||||
|     }) |     }) | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| fn wrap_multiple_with_constr(index: u64, data: Vec<PlutusData>) -> PlutusData { | fn wrap_multiple_with_constr(index: u64, data: Vec<PlutusData>) -> PlutusData { | ||||||
|  |     let converted = convert_constr_to_tag(index); | ||||||
|     PlutusData::Constr(Constr { |     PlutusData::Constr(Constr { | ||||||
|         tag: constr_index(index), |         tag: converted.unwrap_or(ANY_TAG), | ||||||
|         any_constructor: None, |         any_constructor: converted.map_or(Some(index), |_| None), | ||||||
|         fields: data, |         fields: data, | ||||||
|     }) |     }) | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| fn empty_constr(index: u64) -> PlutusData { | fn empty_constr(index: u64) -> PlutusData { | ||||||
|  |     let converted = convert_constr_to_tag(index); | ||||||
|     PlutusData::Constr(Constr { |     PlutusData::Constr(Constr { | ||||||
|         tag: constr_index(index), |         tag: converted.unwrap_or(ANY_TAG), | ||||||
|         any_constructor: None, |         any_constructor: converted.map_or(Some(index), |_| None), | ||||||
|         fields: vec![], |         fields: vec![], | ||||||
|     }) |     }) | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| /// Translate constructor index to cbor tag.
 |  | ||||||
| fn constr_index(index: u64) -> u64 { |  | ||||||
|     121 + index |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| pub trait ToPlutusData { | pub trait ToPlutusData { | ||||||
|     fn to_plutus_data(&self) -> PlutusData; |     fn to_plutus_data(&self) -> PlutusData; | ||||||
| } | } | ||||||
|  |  | ||||||
		Loading…
	
		Reference in New Issue
	
	 Ales
						Ales