mirror of
https://github.com/owntone/owntone-server.git
synced 2025-11-07 12:53:00 -05:00
[db] Move calculation of artist/album id's from sqlite to code
The purpose of this is to support library backends making their own calculation of these id's, which is relevant if they have more information available than just album_artist and album. This also removes a bunch of sqlite extension code plus some triggers, which in itself is probably an improvement.
This commit is contained in:
186
sqlext/sqlext.c
186
sqlext/sqlext.c
@@ -31,183 +31,6 @@
|
||||
#include <sqlite3ext.h>
|
||||
SQLITE_EXTENSION_INIT1
|
||||
|
||||
|
||||
/*
|
||||
* MurmurHash2, 64-bit versions, by Austin Appleby
|
||||
*
|
||||
* Code released under the public domain, as per
|
||||
* <http://murmurhash.googlepages.com/>
|
||||
* as of 2010-01-03.
|
||||
*/
|
||||
|
||||
#if SIZEOF_VOID_P == 8 /* 64bit platforms */
|
||||
|
||||
static uint64_t
|
||||
murmur_hash64(const void *key, int len, uint32_t seed)
|
||||
{
|
||||
const int r = 47;
|
||||
const uint64_t m = 0xc6a4a7935bd1e995;
|
||||
|
||||
const uint64_t *data;
|
||||
const uint64_t *end;
|
||||
const unsigned char *data_tail;
|
||||
uint64_t h;
|
||||
uint64_t k;
|
||||
|
||||
h = seed ^ (len * m);
|
||||
data = (const uint64_t *)key;
|
||||
end = data + (len / 8);
|
||||
|
||||
while (data != end)
|
||||
{
|
||||
k = *data++;
|
||||
|
||||
k *= m;
|
||||
k ^= k >> r;
|
||||
k *= m;
|
||||
|
||||
h ^= k;
|
||||
h *= m;
|
||||
}
|
||||
|
||||
data_tail = (const unsigned char *)data;
|
||||
|
||||
switch (len & 7)
|
||||
{
|
||||
case 7:
|
||||
h ^= (uint64_t)(data_tail[6]) << 48;
|
||||
case 6:
|
||||
h ^= (uint64_t)(data_tail[5]) << 40;
|
||||
case 5:
|
||||
h ^= (uint64_t)(data_tail[4]) << 32;
|
||||
case 4:
|
||||
h ^= (uint64_t)(data_tail[3]) << 24;
|
||||
case 3:
|
||||
h ^= (uint64_t)(data_tail[2]) << 16;
|
||||
case 2:
|
||||
h ^= (uint64_t)(data_tail[1]) << 8;
|
||||
case 1:
|
||||
h ^= (uint64_t)(data_tail[0]);
|
||||
h *= m;
|
||||
}
|
||||
|
||||
h ^= h >> r;
|
||||
h *= m;
|
||||
h ^= h >> r;
|
||||
|
||||
return h;
|
||||
}
|
||||
|
||||
#elif SIZEOF_VOID_P == 4 /* 32bit platforms */
|
||||
|
||||
static uint64_t
|
||||
murmur_hash64(const void *key, int len, uint32_t seed)
|
||||
{
|
||||
const int r = 24;
|
||||
const uint32_t m = 0x5bd1e995;
|
||||
|
||||
const uint32_t *data;
|
||||
const unsigned char *data_tail;
|
||||
uint32_t k1;
|
||||
uint32_t h1;
|
||||
uint32_t k2;
|
||||
uint32_t h2;
|
||||
|
||||
uint64_t h;
|
||||
|
||||
h1 = seed ^ len;
|
||||
h2 = 0;
|
||||
|
||||
data = (const uint32_t *)key;
|
||||
|
||||
while (len >= 8)
|
||||
{
|
||||
k1 = *data++;
|
||||
k1 *= m; k1 ^= k1 >> r; k1 *= m;
|
||||
h1 *= m; h1 ^= k1;
|
||||
|
||||
k2 = *data++;
|
||||
k2 *= m; k2 ^= k2 >> r; k2 *= m;
|
||||
h2 *= m; h2 ^= k2;
|
||||
|
||||
len -= 8;
|
||||
}
|
||||
|
||||
if (len >= 4)
|
||||
{
|
||||
k1 = *data++;
|
||||
k1 *= m; k1 ^= k1 >> r; k1 *= m;
|
||||
h1 *= m; h1 ^= k1;
|
||||
len -= 4;
|
||||
}
|
||||
|
||||
data_tail = (const unsigned char *)data;
|
||||
|
||||
switch(len)
|
||||
{
|
||||
case 3:
|
||||
h2 ^= (uint32_t)(data_tail[2]) << 16;
|
||||
case 2:
|
||||
h2 ^= (uint32_t)(data_tail[1]) << 8;
|
||||
case 1:
|
||||
h2 ^= (uint32_t)(data_tail[0]);
|
||||
h2 *= m;
|
||||
};
|
||||
|
||||
h1 ^= h2 >> 18; h1 *= m;
|
||||
h2 ^= h1 >> 22; h2 *= m;
|
||||
h1 ^= h2 >> 17; h1 *= m;
|
||||
h2 ^= h1 >> 19; h2 *= m;
|
||||
|
||||
h = h1;
|
||||
h = (h << 32) | h2;
|
||||
|
||||
return h;
|
||||
}
|
||||
|
||||
#else
|
||||
# error Platform not supported
|
||||
#endif
|
||||
|
||||
static void
|
||||
sqlext_daap_songalbumid_xfunc(sqlite3_context *pv, int n, sqlite3_value **ppv)
|
||||
{
|
||||
const char *album_artist;
|
||||
const char *album;
|
||||
char *hashbuf;
|
||||
sqlite3_int64 result;
|
||||
|
||||
if (n != 2)
|
||||
{
|
||||
sqlite3_result_error(pv, "daap_songalbumid() requires 2 parameters, album_artist and album", -1);
|
||||
return;
|
||||
}
|
||||
|
||||
if ((sqlite3_value_type(ppv[0]) != SQLITE_TEXT)
|
||||
|| (sqlite3_value_type(ppv[1]) != SQLITE_TEXT))
|
||||
{
|
||||
sqlite3_result_error(pv, "daap_songalbumid() requires 2 text parameters", -1);
|
||||
return;
|
||||
}
|
||||
|
||||
album_artist = (const char *)sqlite3_value_text(ppv[0]);
|
||||
album = (const char *)sqlite3_value_text(ppv[1]);
|
||||
|
||||
hashbuf = sqlite3_mprintf("%s==%s", (album_artist) ? album_artist : "", (album) ? album : "");
|
||||
if (!hashbuf)
|
||||
{
|
||||
sqlite3_result_error(pv, "daap_songalbumid() out of memory for hashbuf", -1);
|
||||
return;
|
||||
}
|
||||
|
||||
/* Limit hash length to 63 bits, due to signed type in sqlite */
|
||||
result = murmur_hash64(hashbuf, strlen(hashbuf), 0) >> 1;
|
||||
|
||||
sqlite3_free(hashbuf);
|
||||
|
||||
sqlite3_result_int64(pv, result);
|
||||
}
|
||||
|
||||
static void
|
||||
sqlext_daap_no_zero_xfunc(sqlite3_context *pv, int n, sqlite3_value **ppv)
|
||||
{
|
||||
@@ -278,15 +101,6 @@ sqlite3_extension_init(sqlite3 *db, char **pzErrMsg, const sqlite3_api_routines
|
||||
SQLITE_EXTENSION_INIT2(pApi);
|
||||
int ret;
|
||||
|
||||
ret = sqlite3_create_function(db, "daap_songalbumid", 2, SQLITE_UTF8, NULL, sqlext_daap_songalbumid_xfunc, NULL, NULL);
|
||||
if (ret != SQLITE_OK)
|
||||
{
|
||||
if (pzErrMsg)
|
||||
*pzErrMsg = sqlite3_mprintf("Could not create daap_songalbumid function: %s\n", sqlite3_errmsg(db));
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
ret = sqlite3_create_function(db, "daap_no_zero", 2, SQLITE_UTF8, NULL, sqlext_daap_no_zero_xfunc, NULL, NULL);
|
||||
if (ret != SQLITE_OK)
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user