Why does hashing the same vector twice get different hash codes? - vector

I want to get the hash code of this vector:
let vec = vec![1,2,3];
let tmp = vec![1,2,3];
let mut hash = DefaultHasher::new();
vec.hash(&mut hash);
println!("{}", hash.finish());
tmp.hash(&mut hash);
println!("{}", hash.finish());
However the output is:
13585085576907263210
8618793686565720431
What's going on? I have tried multiple times and always get the same result. I want the vector with the same elements to hash to the same hash code.

The hasher is not reset after finish. Create a new hasher state with DefaultHasher::new() for each hash value you want to compute.

Related

Rust: How to input a custom string to convert into ciphertext using Kyber1024

So I would like to make a function in Rust where I can input a string and get the ciphertext out of it. I'm using the Kyber1024 KEM and I can't find a way to input a custom string to turn into a cipher.
Documentation: https://docs.rs/pqcrypto-kyber/0.7.6/pqcrypto_kyber/kyber1024/index.html
Crate: https://crates.io/crates/pqcrypto-kyber
The usage in the documentation just says this:
use pqcrypto_kyber::kyber1024::*;
let (pk, sk) = keypair();
let (ss1, ct) = encapsulate(&pk);
let ss2 = decapsulate(&ct, &sk);
assert!(ss1 == ss2);
Nowhere does it illustrate (as far as I can see) a way for a user to insert a custom string for example so it can get converted into ciphertext.
How do I do this?

How does timestamp hashing work?

Suppose you have an existing hash g84t5tw73y487tb38wo4bq8o34q384o7nfw3q434hqa which was created from the original string dont downvote my stupid question
Now I timestamp this hash like this (in JS/pseudo-code):
var hash = 'g84t5tw73y487tb38wo4bq8o34q384o7nfw3q434hqa';
var today= new Date(); // 2017-10-19
var timestamped = hash + today;
var new_hash = SHA256(timestamped);
// new_hash is 34t346tf3847tr8qrot3r8q248rtbrq4brtqti4t
If I wanted to verify my original string I can do:
var verified = goodHash('dont downvote my stupid question',hash); // true
If I wanted to verify the timestamped version I can do:
var original_hash = 'g84t5tw73y487tb38wo4bq8o34q384o7nfw3q434hqa';
var today = '2017-10-19';
var verified = goodHash(original_hash+today, timestamped_hash); // true
But if I tried to verify the original string against the timestamp, I CANT do:
var today = '2017-10-19';
var verified = goodHash('dont downvote my stupid question'+today, timestamped_hash); // FALSE
Now suppose this original string is hashed and timestamped over and over again for n iterations.
I would only ever be able to verify the n-1th timestamp, provided I have the n-1th hash.
But what if I have the original string dont downvote my stupid question and want to verify any ith timestamp, where 0 < i < n.
Basically, I want to verify whether a string that only I should have knowledge of, has been timestamped with a given date, regardless of how many times it may have been timestamped and without increasing the length of the string (too much - although any increase in length would approach infinity as n grows).
Is this even possible? Can a hash even contain all this information?
Let's look at the mathematics involved here:
First, you have a input string s and a sequence t of timestamps. I will use t[i] to denote the ith timestamp. Your repeated hashing is a recurrence relation:
f(i) = hash(f(t[i-1]) + t[i])
Where + denotes string concatenation. Now we want to determine if there is a closed formula F(x) which will calculate the ith hash with less time-complexity than evaluating the recurrence relation f(i).
One way to accomplish this is to find a string x(i) with the same hash as f(t[i-1]) + t[i]. For a good hashing algorithm, these collisions are exceedingly rare. My gut instinct is that finding such a string (other than f(t[i-1]) + t[i] itself) is more difficult than simply calculating directly from the recurrence relation.

Swift dictionary keys are integers

I have an app that I'm converting from Swift2 to Swift3. One thing I need to do is the following:
dict.enumerateKeysAndObjects({ (key, rotationString, stop) -> Void in
//code goes here to use key as an integer
)
How do I do that? Also, rotationString will also be an integer.
Background:
In the Swift2 version of the app I was saving data to defaults thusly:
func saveGame() {
let defaults = UserDefaults.standard
defaults.set(blackRotations, forKey: "blackRotations")
defaults.set(whiteRotations, forKey: "whiteRotations")
etc.
Here, whiteRotations and blackRotations were NSDictionary objects where the actual data being saved had keys that were NSNumbers and values that were also NSNumbers.
So, what I need to do is to handle loading the saved game from UserDefaults. The values for blackRotations and whiteRotations were dictionaries when the game was saved. The structure of this dictionary was a bunch of integer pairs. You can think of them as integer lookup tables saved as dictionaries.
So all I really am asking for is how to load this data from UserDefaults and be able to treat both the keys and values as integers.
Possible solution? I'm still working on trying to get this to work, but I'll post here anyway, in the hope that it will help to illustrate what I am trying to do.
In the method that loads the saved state, I think I need to do something along these lines:
if let blackDict = (defaults.dictionary(forKey: "blackRotations") as? [String:Int]) {
for (keyString, rotation) in blackDict {
blackRotations[Int(keyString)!] = rotation
}
}

How do I convert a vector of strings to a vector of integers in a functional way?

I'm trying to convert Vec<&str> to Vec<u16> but I can't figure out a functional way to do it.
let foo: &str = "1,2,3"; // Parsing a string here
let bar: Vec<&str> = foo.split(",").collect(); // Bar is a nice vector of &str's
I need to get bar into a Vec<u16>.
There's an iterator adapter map! You'd use it like this:
let bar: Vec<u16> = foo.split(",").map(|x| x.parse::<u16>().unwrap()).collect();
parse is a library function that relies on the trait FromStr, and it can return an error, so we need to unwrap() the error type. (This is a good idea for a short example, but in real code, you will want to handle the error properly - if you have a value that's not a u16 there, your program will just crash).
map takes a closure that takes it's parameter by value and then returns the iterator obtained by lazily applying that function. You're collecting all of the values here, but if you only take(5) of them, you would only parse 5 of the strings.
You haven't fully specified your problem. Specifically, what should happen when one of the strings cannot be parsed into a number? When you parse a number from a string using parse, it can fail. That is why the function returns a Result:
fn parse<F>(&self) -> Result<F, F::Err>
where
F: FromStr,
Here's a solution that takes the vector, gets an iterator with iter, changes each item using map and ultimately returns a Result using collect. If the parsing was a success, you get an Ok. If any failed, you get an Err:
fn main() {
let input = "1,2,3";
let strings: Vec<_> = input.split(",").collect();
let numbers: Result<Vec<u16>, _> = strings.iter().map(|x| x.parse()).collect();
println!("{:?}", numbers);
}
Or you could remove failed conversions by filtering out Err values with flat_map:
fn main() {
let input = "1,2,3";
let strings: Vec<_> = input.split(",").collect();
let numbers: Vec<u16> = strings.iter().flat_map(|x| x.parse()).collect();
println!("{:?}", numbers);
}
Of course, it's a bit silly to convert the string into a vector of strings and then convert it again to a vector of integers. If you actually have a comma-separated string and want numbers, do it in one go:
fn main() {
let input = "1,2,3";
let numbers: Result<Vec<u16>, _> = input.split(",").map(|x| x.parse()).collect();
println!("{:?}", numbers);
}
See also:
Why does `Option` support `IntoIterator`?
My take as someone not really experienced in Rust yet.
fn main() {
let foo: &str = "1,2,3"; // Parsing a string here
let bar: Vec<&str> = foo.split(",").collect(); // Bar is a nice vector of &str's
// here the magic happens
let baz = bar.iter().map(|x| x.parse::<i64>());
for x in baz {
match x {
Ok(i) => println!("{}", i),
Err(_) => println!("parse failed"),
}
}
}
Note that since parse returns a Result, you have to extract the value from each parsed element. You might want to behave in a different way, e.g. filter only the succeeded results.

How can I unpack (destructure) elements from a vector?

I am currently doing the following:
let line_parts = line.split_whitespace().take(3).collect::<Vec<&str>>();
let ip = line_parts[0];
let bytes = line_parts[1];
let int_number = line_parts[2];
Is it possible to do something like this?
let [ip, bytes, int_number] = line.split_whitespace().take(3).collect();
I'm noticed various references to vector destructuring on some sites but the official docs don't seem to mention it.
It seems what you need is "slice patterns":
fn main() {
let line = "127.0.0.1 1000 what!?";
let v = line.split_whitespace().take(3).collect::<Vec<&str>>();
if let [ip, port, msg] = &v[..] {
println!("{}:{} says '{}'", ip, port, msg);
}
}
Playground link
Note the if let instead of plain let. Slice patterns are refutable, so we need to take this into account (you may want to have an else branch, too).
You can also use this:
use std::convert::TryFrom;
let v = line.split_whitespace().take(3).collect::<Vec<&str>>();
let [ip, bytes, int_number] = <[&str; 3]>::try_from(v).ok().unwrap();
The return type of <[&str; 3]>::try_from(v) will be the Result type which you can use for error handling or allow it to panic as I did, since we already know that the size is 3.

Resources