Avatar billede benneharli Juniormester
21. juni 2017 - 14:35 Der er 10 kommentarer og
2 løsninger

java.util.zip.CRC32 i C#

Hejsa,

Skal konvertere noget Java til C#... generelt ret enkelt, men hvad gør man lige når .NET ikke umiddelbart har samme funktion/klasse som Java?

Her er Java koden:

import java.util.zip.CRC32;

SimpleDateFormat dateFormat = new SimpleDateFormat("yyyyMMdd");
String dateNow = dateFormat.format(new Date());
String secret = "megetHemmeligKodeJegIkkeMåDele";
CRC32 digest = new CRC32();
try
{
  digest.update(dateNow.getBytes("UTF-8"));
  digest.update(MainWindow.this.sessionText.getText().toUpperCase().getBytes("UTF-8"));
  digest.update(secret.getBytes("UTF-8"));
  long hash = digest.getValue();
  MainWindow.this.recoveredText.setText(String.format("%08X", new Object[] { Long.valueOf(hash) }));
}
catch (UnsupportedEncodingException e)
{
  e.printStackTrace();
}
Avatar billede arne_v Ekspert
21. juni 2017 - 14:58 #1
Du har et par muligheder.

Du kan hente en CRC32 pakke med NuGet og konvertere kaldene.

Eller du kan lave en ref til vjslib.dll og bruge java.util.zip.CRC32!!!!

(.NET understoetter J# sproget som saadan cirka er Java 1.1 og den klasse eksisterede allerede dengang)
Avatar billede benneharli Juniormester
21. juni 2017 - 15:10 #2
Ville helst undgå ekstra dll'er og .NET referencer der evt. ikke er inkluderet.

Hvilken CRC32 pakke mener du præcist? Der er flere at vælge imellem.
Avatar billede arne_v Ekspert
21. juni 2017 - 15:47 #3
Jeg tror at vjslib.dll kommer med .NET selv.

Har du en "ren" (ikke-udviklings) maskine som du kan teste?

Lad mig proeve at lege med lidt kode.
Avatar billede arne_v Ekspert
21. juni 2017 - 16:40 #4
java.util.zip.CRC32
SharpZipLib
HashLib via NuGet


using System;
using System.Linq;
using System.Text;

using java.util.zip;

using ICSharpCode.SharpZipLib.Checksums;

using HashLib;

namespace E
{
    public class Program
    {
        public static void TestVJSLIB(string s)
        {
            sbyte[] b = Encoding.UTF8.GetBytes(s).Select(v => (sbyte)v).ToArray();
            CRC32 crc = new CRC32();
            crc.update(b);
            long crcval = crc.getValue();
            Console.WriteLine("{0:X}", crcval);
        }
        public static void TestSharpZipLib(string s)
        {
            byte[] b = Encoding.UTF8.GetBytes(s);
            Crc32 crc = new Crc32();
            crc.Update(b);
            long crcval = crc.Value;
            Console.WriteLine("{0:X}", crcval);
        }
        public static void TestHashLib(string s)
        {
            byte[] b = Encoding.UTF8.GetBytes(s);
            IHash crc = HashFactory.Checksum.CreateCRC32a();
            uint crcval = crc.ComputeBytes(b).GetUInt();
            Console.WriteLine("{0:X}", crcval);
        }
        public static void Main(string[] args)
        {
            string s = "This is a small test";
            TestVJSLIB(s);
            TestSharpZipLib(s);
            TestHashLib(s);
            Console.ReadKey(true);
        }
    }
}


Output:

4A6C7DD7
4A6C7DD7
4A6C7DD7
Avatar billede benneharli Juniormester
21. juni 2017 - 16:53 #5
Nice! Giver det lige et skud og vender tilbage. Skal lige teste det mod en jar fil.
Avatar billede benneharli Juniormester
21. juni 2017 - 22:46 #6
Yes sir! tak - det blev med SharpZipLib - så må de leve med en ekstra dll.

Hyg
Avatar billede arne_v Ekspert
21. juni 2017 - 23:03 #7
Alternativet maa vaere at lave en egen implementation af algoritmen.
Avatar billede benneharli Juniormester
21. juni 2017 - 23:45 #8
Hvilket jeg også var ude i ved at sakse lidt rundt omkring, men det blev lidt rodet til sidst... manuelt "table" osv...
Avatar billede arne_v Ekspert
22. juni 2017 - 04:01 #9
CRC beregning er noget "bit griseri".

:-)

Min version:


using System;
using System.Linq;
using System.Text;

using java.util.zip;

using ICSharpCode.SharpZipLib.Checksums;

using HashLib;

namespace E
{
    public class Program
    {
        public static void TestVJSLIB(string s)
        {
            sbyte[] b = Encoding.UTF8.GetBytes(s).Select(v => (sbyte)v).ToArray();
            CRC32 crc = new CRC32();
            crc.update(b);
            long crcval = crc.getValue();
            Console.WriteLine("{0:X}", crcval);
        }
        public static void TestSharpZipLib(string s)
        {
            byte[] b = Encoding.UTF8.GetBytes(s);
            Crc32 crc = new Crc32();
            crc.Update(b);
            long crcval = crc.Value;
            Console.WriteLine("{0:X}", crcval);
        }
        public static void TestHashLib(string s)
        {
            byte[] b = Encoding.UTF8.GetBytes(s);
            IHash crc = HashFactory.Checksum.CreateCRC32a();
            uint crcval = crc.ComputeBytes(b).GetUInt();
            Console.WriteLine("{0:X}", crcval);
        }
        public class MyCRC
        {
            private uint init;
            private int step;
            private int limit;
            private int ix;
            private uint[] table;
            private uint mask;
            public MyCRC(uint poly, uint init, int step, int limit, int ix)
            {
                this.init = init;
                this.step = step;
                this.limit = limit;
                this.ix = ix;
                table = new uint[16];
                mask = 0xFFU >> (8 - step);
                for(int i = 0; i < 16; i++)
                {
                    uint tmp = (uint)i;
                    for(int j = 0; j < 4; j++)
                    {
                        uint x = tmp & 1;
                        tmp = tmp >> 1;
                        if(x == 1) tmp = tmp ^ poly;
                    }
                    table[i] = tmp;
                }
            }
            public virtual uint Compute(byte[] b)
            {
                uint res = init;
                for(int j = 0; j < b.Length; j++)
                {
                    res = res ^ b[j];
                    for(int i = 0; i < limit; i++)
                    {
                        res = (uint)((res >> step) ^ table[(res & mask) * ix]);
                    }
                }
                return res;
            }
        }
        public class MyCRC32 : MyCRC
        {
            public MyCRC32() : base(0xEDB88320, 0xFFFFFFFF, 4, 2, 1)
            {
            }
            public override uint Compute(byte[] b)
            {
                return base.Compute(b) ^ 0xFFFFFFFF;
            }
        }
        public static void TestDIY(string s)
        {
            byte[] b = Encoding.UTF8.GetBytes(s);
            MyCRC32 crc = new MyCRC32();
            uint crcval = crc.Compute(b);
            Console.WriteLine("{0:X}", crcval);           
        }
        public static void Main(string[] args)
        {
            string s = "This is a small test";
            TestVJSLIB(s);
            TestSharpZipLib(s);
            TestHashLib(s);
            TestDIY(s);
            Console.ReadKey(true);
        }
    }
}
Avatar billede arne_v Ekspert
22. juni 2017 - 04:03 #10
Jeg regner med at I er klar over at CRC er fremragende til at detektere data korruption via uheld (transmissions fejl og ligenden) men daarligt til at detektere data korruption via bevist manipulation.

CRC er ikke kryptografisk staerk som rigtige hash a la SHA-256.
Avatar billede benneharli Juniormester
22. juni 2017 - 06:36 #11
Ha, må jeg lige lure på :-) spændende!
Klart. Bruger normalt selv CRC til checksums beregning i Modbus kommunikation (RS485 bus)... eller man gør... det er ikke mig der har opfundet den dybe tallerken :-)

Her er det nogen der hasher dato, nøgle og et id for at generere en reset kode, så hvor kryptografisk stærkt det er, er ikke så vigtigt lige her. Det lokale program og enheden skal bare give samme hash, så pin kan resettes... hvis man ikke har nøglen og ved hvad der bliver hashet, så kommer man jo ikke så langt :-)

Tak igen!
Avatar billede benneharli Juniormester
22. juni 2017 - 12:07 #12
Ha! fedt :-)

DIY fungerede også... skulle lige lægge bytes sammen først (der er tre ting der bliver hashet, men det gik fint. Tusinde tak!

                byte[] d = Encoding.UTF8.GetBytes(dateNow);
                byte[] id = Encoding.UTF8.GetBytes(txtSessionID.Text.Trim());
                byte[] s = Encoding.UTF8.GetBytes(secret);

                uint hash = digest.Compute(Combine(d, id, s));

        byte[] Combine(byte[] a1, byte[] a2, byte[] a3)
        {
            byte[] ret = new byte[a1.Length + a2.Length + a3.Length];
            Array.Copy(a1, 0, ret, 0, a1.Length);
            Array.Copy(a2, 0, ret, a1.Length, a2.Length);
            Array.Copy(a3, 0, ret, a1.Length + a2.Length, a3.Length);
            return ret;
        }
Avatar billede Ny bruger Nybegynder

Din løsning...

Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.

Loading billede Opret Preview

Log ind eller opret profil

Hov!

For at kunne deltage på Computerworld Eksperten skal du være logget ind.

Det er heldigvis nemt at oprette en bruger: Det tager to minutter og du kan vælge at bruge enten e-mail, Facebook eller Google som login.

Du kan også logge ind via nedenstående tjenester