-
Notifications
You must be signed in to change notification settings - Fork 13
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
fix: :i8 vs :byte #158
Comments
(slack comment) Could it be that i8 translates to 2 bytes because integers are naturally signed in Java ? So that in order to represent (nonnegative) 8bit integers you need 9 bits and so 2 bytes ? |
Nearly, as can be seen here. This comes from unsigned bytes being very finicky to handle in Java, hence the choice to “waste” a byte, but use an integer type that will behave more intuitively. |
@OlivierBBB I have checked the specs and it says
thus
So, while reducing the size of |
Whilst this is technically true, you can always represent them as bytes in the correct way. It does require a bit of Java trickery to do it correctly though. |
Right, yeah. I have experience with this though. So, I can fix it. |
@lorenzogentile404 Are we getting concerned about the size of trace files? |
@lorenzogentile404 @delehef Ok, I put together a patch on the branch In the end, I just followed the existing implementation for Thoughts? |
commented, imho we should separate the case :i1 which is in both case 1 and case 1..8. |
I'm not sure, to be honest. When I was printing values for RawMagma::Integer(b) => {
if x.bit_size() > *b {
bail!(RuntimeError::InvalidValue("integer", x))
} else {
Ok(x)
} then |
Ok, that's a fair point. Technically it will always choose the first case in the order so there is no ambiguity. But still better to be explicit about it. I will correct that. |
Ok, corrected on the branch |
Ok, @ivokub I feel like there is some missing context here. What's actually going on here? Is that line of code triggering a panic? For which module? I see that sequence is in |
@delehef Also looking back at the code for the
For example, EDIT: am just trying to figure out how this is all working 🤔 Ok, so case in point. From public Trace wordComparisonStamp(final long b) {
...
wordComparisonStamp.putLong(b);
...
} This is called from void trace(Trace trace, int stamp) {
...
for (int ct = 0; ct <= this.maxCt(); ct++) {
trace
.wordComparisonStamp(stamp) Which in turn is called from public void commit(List<MappedByteBuffer> buffers) {
final Trace trace = new Trace(buffers);
int stamp = 0;
for (WcpOperation operation : this.operations) {
stamp++;
operation.trace(trace, stamp);
}
} So, |
So, for the context - I had received a trace and trace, err := C.trace_compute_from_file(
corset,
C.CString("/home/ivo/temp/cur/1_1672648872179459994.lt"),
C.uint(numberOfThreads),
false,
) doing this, I received the error
It looks like the validation was happening in the snippet in RawMagma::Integer(b) => {
if x.bit_size() > *b {
println!("{} > {}: {}", x.bit_size(), b, x);
bail!(RuntimeError::InvalidValue("integer", x))
} else {
Ok(x)
}
} then I see:
So the value is pub enum Value {
BigInt(BigInt),
#[serde(with = "FrDef")]
Native(Fr),
#[serde(skip)]
ExoNative(Vec<Fr>),
}
pub(crate) fn bit_size(&self) -> usize {
match self {
Value::BigInt(i) => i.bits() as usize,
Value::Native(_) => crate::constants::FIELD_BITSIZE,
Value::ExoNative(fs) => fs.len() * crate::constants::FIELD_BITSIZE,
}
} @lorenzogentile404 has sent me new traces, I'll check with them. But if it only omits the module, then I think that the underlying issue (the column is defined as (sorry if I have missed something which has already been fixed) |
And this still appears with the update trace but in a different location (now failing where we have a colum defined as I'm uploading the zkevm.bin and the trace I have received, the corresponding method in Rust is https://drive.google.com/file/d/1kTtALDaoRYqlvQ07P26kld_9DWxPlDOA/view?usp=sharing, https://drive.google.com/file/d/1sVIYWxtcf-iomzlBhj7izT-LtraPdPNF/view?usp=sharing |
It should be automatically casted to a |
@ivokub are you 100% that versions of the corset you use to check, the corset that was used to generate the Java API, the constraints you use, and the constraints that were used to generate the java traces are all the same? |
@delehef
|
I'm using the same corset version |
Yeah, I understand that. I'm just not sure why it is being upgraded? From what I can understand of this issue, the problem is that e.g. 2 bytes are being packed into an lt trace for an i8 when corset is expecting at most 8bits ... so its throwing a wobbly. Is that about right? But then i'm even more confused. Because, basically, anytime we're using e.g. and i32 or an i64 in the constraints the same thing is gonna happen, no? It'll pack 8bytes for an i32 ... which corset will not like. So ... whats changed thats exposed this issue now? Anyways, I'm aways to Zzzz now. Can revisit this on Monday. |
@DavePearce @ivokub I suggest to have a call about this on Monday, so as we can ensure we are all on the same page regarding the issues we need to address and what has been done up to now. |
@lorenzogentile404 Are you running |
No, I did not. What is it for? Now I get the same error @ivokub got at least.
|
@ivokub Thanks, the context is helping. Presumably, one way this could arise would be if the trace was generated for a @lorenzogentile404 Call on Monday morning European time can work for me --- just put something in the calendar. That'll be Monday evening for me, so I will have had a chance to get up to speed with this :) |
Yay, progress :) The |
Depends on how the column is declared in the constraints. |
@lorenzogentile404 I mean the version of the constraints used to generate the |
I think in this case STAMP is declared i32, which is consistent with Corset translating it as a lo ng. |
Yep, that's why. |
Right, but doesn't it seem odd? Int -> int -> long -> 8bytes -> field representing int (i32). Anyways, no dramas. I need to study the trace filling in more detail. |
Ok, some concrete data / from the traces /
Overall, that looks consistent with two explanations:
I will investigate (2) now. Actually, I think its the most likely as well, since older versions of UPDATE: Can also confirm that at the offending line: RawMagma::Integer(b) => {
if x.bit_size() > *b {
println!("BITWIDTH: {}, B: {b}",x.bit_size());
bail!(RuntimeError::InvalidValue("integer", x))
} else {
Ok(x)
}
} We get UPDATE: Can also eliminate the
Which is consistent with |
Ok, I have a minimal test case now for reproduction:
Using a generated trace file containing column |
Also, worth noting, when
|
So, the very rough sequence is:
impl TryFrom<BigInt> for Value {
type Error = errors::RuntimeError;
fn try_from(int: BigInt) -> Result<Self, Self::Error> {
if int.bits() as usize > constants::FIELD_BITSIZE {
return Err(errors::RuntimeError::InvalidValue(
"field element",
Value::BigInt(int),
));
}
let mut v = Value::BigInt(int);
if *crate::IS_NATIVE.read().unwrap() {
v.to_native();
}
Result::Ok(v)
}
}
So, the validation logic seems to be broken when used in conjunction with the |
This puts through a fix for validation of imported values when `native` fields are being used. The issue is that validation was being performed _after_ conversion into the native field (when this was selected via the `-N` cli switch). Unfortunately, validation at that point cannot work because every field value is assumed to require `254` bits.
Ok, I've rolled back the optimisation around For this issue, I've put together a fix (see above) and raised a PR, inviting some reviewers. @delehef I couldn't seem to add you as a reviewer, but any comments from you would be appreciated. |
This puts through alternative fix for #158 which works for other magma types as well. This does not attempt to bypass the magma validation. Instead, it changes Magma validation so that it no longer uses the `bit_size` of the target value and, instead, checks the target value against the maximum possible value. Specifically, for a value `x` of type `iN` it checks that `x < 2^N`.
This puts through alternative fix for #158 which works for other magma types as well. This does not attempt to bypass the magma validation. Instead, it changes Magma validation so that it no longer uses the `bit_size` of the target value and, instead, checks the target value against the maximum possible value. Specifically, for a value `x` of type `iN` it checks that `x < 2^N`.
This puts through a fix for validation of imported values when `native` fields are being used. The issue is that validation was being performed _after_ conversion into the native field (when this was selected via the `-N` cli switch). Unfortunately, validation at that point cannot work because every field value is assumed to require `254` bits.
If we define
(MSHP :i8)
, we obtainnew ColumnHeader("shfreftable.MSHP", 2, length)
in Java (i.e., 2 bytes, while it should be 1). Instead, if we define(MSHP :byte)
then we obtainnew ColumnHeader("shfreftable.MSHP", 1, length)
, that is what I expected.The text was updated successfully, but these errors were encountered: