google / crclib.dart

Apache License 2.0
23 stars 20 forks source link

Getting incremental CRC value #17

Open dlewis2017 opened 4 months ago

dlewis2017 commented 4 months ago

Hello,

I'm sure this could also be a stack overflow question with this library linked, but I wanted to reach out directly in case this needs to be a potential "enhancement".

So, I'd like to be able to convert chunks of data where, at each update of the sink, I have access to the current CRC value so that I can use that. So far I see startChunkedConversion(), addSlice(), and other functions that seem to be useful for what I need to accomplish, but no way to get intermediary crc value along the way, only getting a final CRC value.

Is there a way to do this currently? Would this need to be added?

Thanks,

postmasters commented 3 months ago

That is the purpose of the split method.

https://github.com/google/crclib.dart/blob/main/lib/src/primitive.dart#L105

After calling that, you can finalize the returned sink.

dlewis2017 commented 3 months ago

Thanks! @postmasters I think that should work. It would be helpful if FinalSink could be exposed and just the type for ParametricCrcSink<dynamic> but in theory, based on what you said, the below should work. I do manage to get it to work when the bytes being sent over BLE are small enough that there's only 1 chunk from C to Dart. But I have not been able to get it working for multiple chunks and going from Dart to C. The C side isn't able to compute a proper CRC based on the value I calculate on the Dart side. I'm pretty sure the polynomials and all variables match even though the other code is C, and I've tried multiple types from the catalog.dart file but still no luck. I'll assume it's some weird mismatch and this issue can be closed.

Another interesting note is that the code here works both Dart to C and C to Dart: https://github.com/kaisellgren/CRC32/blob/master/lib/crc32.dart


  Crc32IsoHdlc crc32 = Crc32IsoHdlc();
  CrcValueCollector outputSink = CrcValueCollector();

      if (currentChunk == 0) {
        final crcSink = crc32.startChunkedConversion(outputSink);
        crcSink.add(totalSegments);
        crcSink.close();
      } else {
        final updatedSink = crcSink.split(outputSink);
        updatedSink.add(totalSegments);
        updatedSink.close();
      }

...

class CrcValueCollector implements Sink<CrcValue> {
  CrcValue? crcValue;

  int get crcValueInt {
    final bigIntVal = crcValue!.toBigInt();
    return bigIntVal.toInt();
  }

  @override
  void add(CrcValue data) {
    crcValue = data;
  }

  @override
  void close() {
    print('CRC Calculation Completed: ${crcValue.toString()}');
  }
}