From 6dd32647b554bcee757edf6dc9c31ce18fd9f6af Mon Sep 17 00:00:00 2001 From: Adam Wick Date: Fri, 7 Feb 2020 16:03:49 -0600 Subject: [PATCH] Fix signed addition and subtraction. --- generation/src/Conversions.hs | 78 +++++++++++++++--------- generation/src/Subtract.hs | 8 +-- generation/src/generation.code-workspace | 11 ++++ 3 files changed, 65 insertions(+), 32 deletions(-) create mode 100644 generation/src/generation.code-workspace diff --git a/generation/src/Conversions.hs b/generation/src/Conversions.hs index ecf32ed..c038d73 100644 --- a/generation/src/Conversions.hs +++ b/generation/src/Conversions.hs @@ -567,8 +567,58 @@ generateSignedCryptonumConversions source otherSizes = concatMap convert otherSi tuName = mkIdent ("U" ++ show target) sEntries = toLit (source `div` 64) tEntries = toLit (target `div` 64) + sTop = toLit ((source `div` 64) - 1) + extensions = map (\ x -> + let xLit = toLit x + in [stmt| res.contents.value[$$(xLit)] = extension; |]) + [(source `div` 64)..((target `div` 64) - 1)] in case compare source target of LT -> [ + [item| + impl<'a> From<&'a $$sName> for $$tsName { + fn from(x: &$$sName) -> $$tsName { + let mut res = $$tsName::zero(); + res.contents.value[0..$$(sEntries)].copy_from_slice(&x.contents.value); + let extension = if x.contents.value[$$(sTop)] & 0x8000_0000_0000_0000 == 0 { + 0 + } else { + 0xFFFF_FFFF_FFFF_FFFFu64 + }; + $@{extensions} + res + } + } + |], + [item| + impl From<$$sName> for $$tsName { + fn from(x: $$sName) -> $$tsName { + $$tsName::from(&x) + } + } + |], + [item| + impl<'a> TryFrom<&'a $$sName> for $$tuName { + type Error = ConversionError; + + + fn try_from(x: &$$sName) -> Result<$$tuName,ConversionError> { + if x.is_negative() { + Err(ConversionError::NegativeToUnsigned) + } else { + Ok($$tuName::from(&x.contents)) + } + } + } + |], + [item| + impl TryFrom<$$sName> for $$tuName { + type Error = ConversionError; + + fn try_from(x: $$sName) -> Result<$$tuName,ConversionError> { + $$tuName::try_from(&x) + } + } + |] ] EQ -> [ [item| @@ -618,33 +668,5 @@ generateSignedCryptonumConversions source otherSizes = concatMap convert otherSi |] ] GT -> [ - [item| - impl From<$$tuName> for $$sName { - fn from(x: $$tuName) -> $$sName { - $$sName::from(&x) - } - } - |], - [item| - impl<'a> From<&'a $$tuName> for $$sName { - fn from(x: &$$tuName) -> $$sName { - panic!("from1") - } - } - |], - [item| - impl From<$$tsName> for $$sName { - fn from(x: $$tsName) -> $$sName { - $$sName::from(&x) - } - } - |], - [item| - impl<'a> From<&'a $$tsName> for $$sName { - fn from(x: &$$tsName) -> $$sName { - panic!("from2") - } - } - |] ] diff --git a/generation/src/Subtract.hs b/generation/src/Subtract.hs index 58d96d7..8d99609 100644 --- a/generation/src/Subtract.hs +++ b/generation/src/Subtract.hs @@ -35,7 +35,7 @@ safeSignedSubtractOps :: File safeSignedSubtractOps = File { predicate = \ me others -> (me + 64) `elem` others, outputName = "safe_ssub", - isUnsigned = True, + isUnsigned = False, generator = declareSafeSignedSubtractOperators, testCase = Just generateSafeSignedTests } @@ -53,7 +53,7 @@ unsafeSignedSubtractOps :: File unsafeSignedSubtractOps = File { predicate = \ _ _ -> True, outputName = "unsafe_ssub", - isUnsigned = True, + isUnsigned = False, generator = declareUnsafeSignedSubtractOperators, testCase = Just generateUnsafeSignedTests } @@ -166,7 +166,7 @@ declareSafeSignedSubtractOperators bitsize _ = type Output = $$dname; fn sub(self, rhs: &$$sname) -> $$dname { - panic!("sub") + $$dname{ contents: &self.contents - &rhs.contents } } } @@ -254,7 +254,7 @@ declareUnsafeSignedSubtractOperators bitsize _ = impl<'a> SubAssign<&'a $$sname> for $$sname { fn sub_assign(&mut self, rhs: &Self) { - panic!("sub_assign") + self.contents -= &rhs.contents; } } diff --git a/generation/src/generation.code-workspace b/generation/src/generation.code-workspace new file mode 100644 index 0000000..a9563b9 --- /dev/null +++ b/generation/src/generation.code-workspace @@ -0,0 +1,11 @@ +{ + "folders": [ + { + "path": "/Users/awick/projects/cryptonum/generation" + }, + { + "path": "/Users/awick/projects/cryptonum/src" + } + ], + "settings": {} +} \ No newline at end of file