diff --git a/firmware/SOURCES b/firmware/SOURCES index fc194fe640..71a11429cd 100644 --- a/firmware/SOURCES +++ b/firmware/SOURCES @@ -269,6 +269,7 @@ common/timefuncs.c common/unicode.c common/vuprintf.c common/zip.c +common/adler32.c /* Display */ scroll_engine.c diff --git a/firmware/common/adler32.c b/firmware/common/adler32.c new file mode 100644 index 0000000000..8f5f85b453 --- /dev/null +++ b/firmware/common/adler32.c @@ -0,0 +1,75 @@ +/*************************************************************************** + * __________ __ ___. + * Open \______ \ ____ ____ | | _\_ |__ _______ ___ + * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / + * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < + * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ + * \/ \/ \/ \/ \/ + * $Id$ + * + * Copyright (C) 2021 James Buren (adaptations from tinf/zlib) + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY + * KIND, either express or implied. + * + ****************************************************************************/ + +#include "adler32.h" +#include "system.h" + +/* adler_32 (derived from tinf adler32 which was taken from zlib) + * Adler-32 algorithm taken from the zlib source, which is + * Copyright (C) 1995-1998 Jean-loup Gailly and Mark Adler + */ +uint32_t adler_32(const void *src, uint32_t len, uint32_t adler32) +{ + const unsigned char *buf = (const unsigned char *)src; + uint32_t s1 = (adler32 & 0xffff); + uint32_t s2 = (adler32 >> 16); + + enum { + A32_BASE = 65521, + A32_NMAX = 5552, + }; + + while (len > 0) { + uint32_t k = MIN(len, A32_NMAX); + uint32_t i; + + for (i = k / 16; i; --i, buf += 16) { + s2 += s1 += buf[0]; + s2 += s1 += buf[1]; + s2 += s1 += buf[2]; + s2 += s1 += buf[3]; + s2 += s1 += buf[4]; + s2 += s1 += buf[5]; + s2 += s1 += buf[6]; + s2 += s1 += buf[7]; + s2 += s1 += buf[8]; + s2 += s1 += buf[9]; + s2 += s1 += buf[10]; + s2 += s1 += buf[11]; + s2 += s1 += buf[12]; + s2 += s1 += buf[13]; + s2 += s1 += buf[14]; + s2 += s1 += buf[15]; + } + + for (i = k % 16; i; --i) { + s1 += *buf++; + s2 += s1; + } + + s1 %= A32_BASE; + s2 %= A32_BASE; + + len -= k; + } + + return (s1 | (s2 << 16)); +} diff --git a/firmware/include/adler32.h b/firmware/include/adler32.h new file mode 100644 index 0000000000..cd5302e869 --- /dev/null +++ b/firmware/include/adler32.h @@ -0,0 +1,29 @@ +/*************************************************************************** + * __________ __ ___. + * Open \______ \ ____ ____ | | _\_ |__ _______ ___ + * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / + * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < + * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ + * \/ \/ \/ \/ \/ + * $Id$ + * + * Copyright (C) 2021 James Buren (adaptations from tinf/zlib) + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY + * KIND, either express or implied. + * + ****************************************************************************/ + +#include + +#ifndef _ADLER32_H +#define _ADLER32_H + +uint32_t adler_32(const void *src, uint32_t len, uint32_t adler32); + +#endif