Skip to content

Commit

Permalink
Merge pull request #425 from Tencent/dev
Browse files Browse the repository at this point in the history
ix crc32 crash on some arm64 devices
  • Loading branch information
lingol authored Mar 26, 2020
2 parents 26f361b + 3e63738 commit cbe0b50
Show file tree
Hide file tree
Showing 4 changed files with 48 additions and 15 deletions.
2 changes: 1 addition & 1 deletion Android/MMKV/mmkvdemo/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,7 @@ repositories {
// }
jcenter()
mavenCentral()
mavenLocal()
// mavenLocal()
}

dependencies {
Expand Down
44 changes: 44 additions & 0 deletions Core/MMKV_OSX.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -30,8 +30,10 @@
# include "MiniPBCoder.h"
# include "ScopedLock.hpp"
# include "ThreadLock.h"
# include <sys/utsname.h>

# ifdef MMKV_IOS
# include "Checksum.h"
# include <sys/mman.h>
# endif

Expand All @@ -45,6 +47,9 @@ using namespace mmkv;
extern ThreadLock *g_instanceLock;
extern MMKVPath_t g_rootDir;

enum { UnKnown = 0, PowerMac = 1, Mac, iPhone, iPod, iPad, AppleTV, AppleWatch };
static void GetAppleMachineInfo(int &device, int &version);

MMKV_NAMESPACE_BEGIN

extern ThreadOnceToken_t once_control;
Expand All @@ -53,6 +58,16 @@ extern void initialize();
void MMKV::minimalInit(MMKVPath_t defaultRootDir) {
ThreadLock::ThreadOnce(&once_control, initialize);

// crc32 instruction requires A10 chip, aka iPhone 7 or iPad 6th generation
int device = 0, version = 0;
GetAppleMachineInfo(device, version);
# ifdef __aarch64__
if ((device == iPhone && version >= 9) || (device == iPad && version >= 7)) {
CRC32 = mmkv::armv8_crc32;
}
# endif
MMKVInfo("Apple Device:%d, version:%d", device, version);

g_rootDir = defaultRootDir;
mkPath(g_rootDir);

Expand Down Expand Up @@ -215,4 +230,33 @@ void MMKV::enumerateKeys(EnumerateBlock block) {

MMKV_NAMESPACE_END

static void GetAppleMachineInfo(int &device, int &version) {
device = UnKnown;
version = 0;

struct utsname systemInfo = {};
uname(&systemInfo);

std::string machine(systemInfo.machine);
if (machine.find("PowerMac") != std::string::npos || machine.find("Power Macintosh") != std::string::npos) {
device = PowerMac;
} else if (machine.find("Mac") != std::string::npos || machine.find("Macintosh") != std::string::npos) {
device = Mac;
} else if (machine.find("iPhone") != std::string::npos) {
device = iPhone;
} else if (machine.find("iPod") != std::string::npos) {
device = iPod;
} else if (machine.find("iPad") != std::string::npos) {
device = iPad;
} else if (machine.find("AppleTV") != std::string::npos) {
device = AppleTV;
} else if (machine.find("AppleWatch") != std::string::npos) {
device = AppleWatch;
}
auto pos = machine.find_first_of("0123456789");
if (pos != std::string::npos) {
version = std::atoi(machine.substr(pos).c_str());
}
}

#endif // MMKV_IOS_OR_MAC
11 changes: 2 additions & 9 deletions Core/crc32/Checksum.h
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@
*/

#pragma once
#ifdef __cplusplus
#ifdef __cplusplus

#include "../MMKVPredef.h"

Expand All @@ -43,17 +43,10 @@ namespace mmkv {
uint32_t armv8_crc32(uint32_t crc, const unsigned char *buf, size_t len);
}

# ifndef MMKV_ANDROID

# define CRC32(crc, buf, len) mmkv::armv8_crc32(crc, buf, len)

# else // Android runs on too many devices, have to check CPU's instruction set dynamically

// have to check CPU's instruction set dynamically
typedef uint32_t (*CRC32_Func_t)(uint32_t crc, const unsigned char *buf, size_t len);
extern CRC32_Func_t CRC32;

# endif // MMKV_ANDROID

# else // __aarch64__

# include <zlib.h>
Expand Down
6 changes: 1 addition & 5 deletions Core/crc32/crc32_armv8.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -22,18 +22,14 @@

#ifdef __aarch64__

# ifdef MMKV_ANDROID

# include <zlib.h>
# include <zlib.h>

static inline uint32_t _crc32Wrap(uint32_t crc, const unsigned char *buf, size_t len) {
return static_cast<uint32_t>(::crc32(crc, buf, static_cast<uInt>(len)));
}

CRC32_Func_t CRC32 = _crc32Wrap;

# endif // MMKV_ANDROID

// targeting armv8 with crc instruction extension
# define TARGET_ARM_CRC __attribute__((target("crc")))

Expand Down

0 comments on commit cbe0b50

Please sign in to comment.