Skip to content

Commit

Permalink
Merge pull request Tencent#222 from Tencent/dev
Browse files Browse the repository at this point in the history
v1.0.18
  • Loading branch information
lingol authored Mar 14, 2019
2 parents cdc95cb + 115c9c8 commit 87eaabe
Show file tree
Hide file tree
Showing 31 changed files with 290 additions and 116 deletions.
2 changes: 1 addition & 1 deletion Android/MMKV/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ buildscript {
jcenter()
}
dependencies {
classpath 'com.android.tools.build:gradle:3.3.0'
classpath 'com.android.tools.build:gradle:3.3.2'
classpath 'com.jfrog.bintray.gradle:gradle-bintray-plugin:1.8.1'
classpath 'digital.wup:android-maven-publish:3.6.2'
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
Expand Down
2 changes: 1 addition & 1 deletion Android/MMKV/gradle.properties
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,6 @@ org.gradle.jvmargs=-Xmx1536m
# http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects
# org.gradle.parallel=true

VERSION_NAME_PREFIX=1.0.17
VERSION_NAME_PREFIX=1.0.18
#VERSION_NAME_SUFFIX=-SNAPSHOT
VERSION_NAME_SUFFIX=
81 changes: 60 additions & 21 deletions Android/MMKV/mmkv/src/main/cpp/MMKV.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -76,7 +76,7 @@ MMKV::MMKV(
, m_fileLock(m_metaFile.getFd())
, m_sharedProcessLock(&m_fileLock, SharedLockType)
, m_exclusiveProcessLock(&m_fileLock, ExclusiveLockType)
, m_isInterProcess((mode & MMKV_MULTI_PROCESS) != 0)
, m_isInterProcess((mode & MMKV_MULTI_PROCESS) != 0 || (mode & CONTEXT_MODE_MULTI_PROCESS) != 0)
, m_isAshmem((mode & MMKV_ASHMEM) != 0) {
m_fd = -1;
m_ptr = nullptr;
Expand Down Expand Up @@ -198,8 +198,10 @@ void MMKV::initializeMMKV(const std::string &rootDir) {

g_rootDir = rootDir;
char *path = strdup(g_rootDir.c_str());
mkPath(path);
free(path);
if (path) {
mkPath(path);
free(path);
}

MMKVInfo("root dir: %s", g_rootDir.c_str());
}
Expand Down Expand Up @@ -341,6 +343,7 @@ void MMKV::loadFromFile() {
} else {
auto strategic = onMMKVFileLengthError(m_mmapID);
if (strategic == OnErrorRecover) {
writeAcutalSize(m_size - Fixed32Size);
loadFromFile = true;
needFullWriteback = true;
}
Expand Down Expand Up @@ -677,8 +680,8 @@ bool MMKV::ensureMemorySize(size_t newSize) {
size_t lenNeeded = data.length() + offset + newSize;
if (m_isAshmem) {
if (lenNeeded > m_size) {
MMKVWarning("ashmem %s reach size limit:%zu, consider configure with larger size",
m_mmapID.c_str(), m_size);
MMKVError("ashmem %s reach size limit:%zu, consider configure with larger size",
m_mmapID.c_str(), m_size);
return false;
}
} else {
Expand Down Expand Up @@ -1211,15 +1214,45 @@ bool MMKV::getVectorForKey(const std::string &key, std::vector<std::string> &res
return false;
}

size_t MMKV::getValueSizeForKey(const std::string &key) {
size_t MMKV::getValueSizeForKey(const std::string &key, bool actualSize) {
if (key.empty()) {
return 0;
}
SCOPEDLOCK(m_lock);
auto &data = getDataForKey(key);
if (actualSize) {
CodedInputData input(data.getPtr(), data.length());
auto length = input.readInt32();
if (pbRawVarint32Size(length) + length == data.length()) {
return static_cast<size_t>(length);
}
}
return data.length();
}

int32_t MMKV::writeValueToBuffer(const std::string &key, void *ptr, int32_t size) {
if (key.empty()) {
return -1;
}
SCOPEDLOCK(m_lock);
auto &data = getDataForKey(key);
CodedInputData input(data.getPtr(), data.length());
auto length = input.readInt32();
auto offset = pbRawVarint32Size(length);
if (offset + length == data.length()) {
if (length <= size) {
memcpy(ptr, (uint8_t *) data.getPtr() + offset, length);
return length;
}
} else {
if (data.length() <= size) {
memcpy(ptr, data.getPtr(), data.length());
return static_cast<int32_t>(data.length());
}
}
return -1;
}

#pragma mark - enumerate

bool MMKV::containsKey(const std::string &key) {
Expand Down Expand Up @@ -1307,28 +1340,32 @@ bool MMKV::isFileValid(const std::string &mmapID) {

uint32_t crcFile = 0;
MMBuffer *data = readWholeFile(crcPath.c_str());
if (data && data->getPtr()) {
MMKVMetaInfo metaInfo;
metaInfo.read(data->getPtr());
crcFile = metaInfo.m_crcDigest;
if (data) {
if (data->getPtr()) {
MMKVMetaInfo metaInfo;
metaInfo.read(data->getPtr());
crcFile = metaInfo.m_crcDigest;
}
delete data;
} else {
return false;
}

const int offset = pbFixed32Size(0);
size_t actualSize = 0;
uint32_t crcDigest = 0;
MMBuffer *fileData = readWholeFile(kvPath.c_str());
if (fileData) {
actualSize = CodedInputData(fileData->getPtr(), fileData->length()).readFixed32();
if (actualSize > fileData->length() - offset) {
delete fileData;
return false;
}

uint32_t crcDigest = (uint32_t) crc32(0, (const uint8_t *) fileData->getPtr() + offset,
(uint32_t) actualSize);
if (fileData->getPtr()) {
size_t actualSize =
CodedInputData(fileData->getPtr(), fileData->length()).readFixed32();
if (actualSize > fileData->length() - offset) {
delete fileData;
return false;
}

crcDigest = (uint32_t) crc32(0, (const uint8_t *) fileData->getPtr() + offset,
(uint32_t) actualSize);
}
delete fileData;
return crcFile == crcDigest;
} else {
Expand All @@ -1338,8 +1375,10 @@ bool MMKV::isFileValid(const std::string &mmapID) {

static void mkSpecialCharacterFileDirectory() {
char *path = strdup((g_rootDir + "/" + SPECIAL_CHARACTER_DIRECTORY_NAME).c_str());
mkPath(path);
free(path);
if (path) {
mkPath(path);
free(path);
}
}

static string md5(const string &value) {
Expand Down
7 changes: 5 additions & 2 deletions Android/MMKV/mmkv/src/main/cpp/MMKV.h
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,8 @@ class AESCrypt;
enum MMKVMode : uint32_t {
MMKV_SINGLE_PROCESS = 0x1,
MMKV_MULTI_PROCESS = 0x2,
MMKV_ASHMEM = 0x4,
CONTEXT_MODE_MULTI_PROCESS = 0x4, // in case someone mistakenly pass Context.MODE_MULTI_PROCESS
MMKV_ASHMEM = 0x8,
};

class MMKV {
Expand Down Expand Up @@ -191,7 +192,9 @@ class MMKV {

bool getVectorForKey(const std::string &key, std::vector<std::string> &result);

size_t getValueSizeForKey(const std::string &key);
size_t getValueSizeForKey(const std::string &key, bool acutalSize);

int32_t writeValueToBuffer(const std::string &key, void *ptr, int32_t size);

bool containsKey(const std::string &key);

Expand Down
3 changes: 3 additions & 0 deletions Android/MMKV/mmkv/src/main/cpp/MmapedFile.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -185,6 +185,9 @@ bool createFile(const std::string &filePath) {
} else {
// create parent dir
char *path = strdup(filePath.c_str());
if (!path) {
return false;
}
auto ptr = strrchr(path, '/');
if (ptr) {
*ptr = '\0';
Expand Down
38 changes: 32 additions & 6 deletions Android/MMKV/mmkv/src/main/cpp/native-bridge.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -160,7 +160,7 @@ static JNIEnv *getCurrentEnv() {

MMKVRecoverStrategic onMMKVCRCCheckFail(const std::string &mmapID) {
auto currentEnv = getCurrentEnv();
if (g_currentJVM && g_callbackOnCRCFailID) {
if (currentEnv && g_callbackOnCRCFailID) {
jstring str = string2jstring(currentEnv, mmapID);
auto strategic = currentEnv->CallStaticIntMethod(g_cls, g_callbackOnCRCFailID, str);
return static_cast<MMKVRecoverStrategic>(strategic);
Expand Down Expand Up @@ -701,14 +701,12 @@ extern "C" JNIEXPORT void JNICALL Java_com_tencent_mmkv_MMKV_close(JNIEnv *env,
}
}

extern "C" JNIEXPORT jint JNICALL Java_com_tencent_mmkv_MMKV_valueSize(JNIEnv *env,
jobject instance,
jlong handle,
jstring oKey) {
extern "C" JNIEXPORT jint JNICALL Java_com_tencent_mmkv_MMKV_valueSize(
JNIEnv *env, jobject instance, jlong handle, jstring oKey, jboolean actualSize) {
MMKV *kv = reinterpret_cast<MMKV *>(handle);
if (kv && oKey) {
string key = jstring2string(env, oKey);
return kv->getValueSizeForKey(key);
return static_cast<jint>(kv->getValueSizeForKey(key, (bool) actualSize));
}
return 0;
}
Expand All @@ -724,3 +722,31 @@ extern "C" JNIEXPORT void JNICALL Java_com_tencent_mmkv_MMKV_setLogReDirecting(J
jboolean enable) {
g_isLogRedirecting = (enable == JNI_TRUE);
}

extern "C" JNIEXPORT jlong JNICALL Java_com_tencent_mmkv_MMKV_createNB(JNIEnv *env,
jobject instance,
jint size) {
auto ptr = malloc(static_cast<size_t>(size));
if (!ptr) {
MMKVError("fail to create NativeBuffer:%s", strerror(errno));
return 0;
}
return reinterpret_cast<jlong>(ptr);
}

extern "C" JNIEXPORT void JNICALL Java_com_tencent_mmkv_MMKV_destroyNB(JNIEnv *env,
jobject instance,
jlong pointer,
jint size) {
free(reinterpret_cast<void *>(pointer));
}

extern "C" JNIEXPORT jint JNICALL Java_com_tencent_mmkv_MMKV_writeValueToNB(
JNIEnv *env, jobject instance, jlong handle, jstring oKey, jlong pointer, jint size) {
MMKV *kv = reinterpret_cast<MMKV *>(handle);
if (kv && oKey) {
string key = jstring2string(env, oKey);
return kv->writeValueToBuffer(key, reinterpret_cast<void *>(pointer), size);
}
return -1;
}
39 changes: 36 additions & 3 deletions Android/MMKV/mmkv/src/main/java/com/tencent/mmkv/MMKV.java
Original file line number Diff line number Diff line change
Expand Up @@ -126,7 +126,10 @@ public static void setLogLevel(MMKVLogLevel level) {

static public final int MULTI_PROCESS_MODE = 0x2;

static private final int ASHMEM_MODE = 0x4;
// in case someone mistakenly pass Context.MODE_MULTI_PROCESS
static private final int CONTEXT_MODE_MULTI_PROCESS = 0x4;

static private final int ASHMEM_MODE = 0x8;

public static MMKV mmkvWithID(String mmapID) {
if (rootDir == null) {
Expand Down Expand Up @@ -436,7 +439,13 @@ public <T extends Parcelable> T decodeParcelable(String key, Class<T> tClass, T
// return the actual size consumption of the key's value
// Note: might be a little bigger than value's length
public int getValueSize(String key) {
return valueSize(nativeHandle, key);
return valueSize(nativeHandle, key, false);
}

// return the actual size of the key's value
// String's length or byte[]'s length, etc
public int getValueActualSize(String key) {
return valueSize(nativeHandle, key, true);
}

public boolean containsKey(String key) {
Expand Down Expand Up @@ -647,6 +656,24 @@ public static MMKV mmkvWithAshmemFD(String mmapID, int fd, int metaFD, String cr

public native int ashmemMetaFD();

// native buffer
public static NativeBuffer createNativeBuffer(int size) {
long pointer = createNB(size);
if (pointer <= 0) {
return null;
}
return new NativeBuffer(pointer, size);
}

public static void destroyNativeBuffer(NativeBuffer buffer) {
destroyNB(buffer.pointer, buffer.size);
}

// return size written, -1 on error
public int writeValueToNativeBuffer(String key, NativeBuffer buffer) {
return writeValueToNB(nativeHandle, key, buffer.pointer, buffer.size);
}

// callback handler
private static MMKVHandler gCallbackHandler;
private static boolean gWantLogReDirecting = false;
Expand Down Expand Up @@ -778,9 +805,15 @@ private MMKV(long handle) {

private native void removeValueForKey(long handle, String key);

private native int valueSize(long handle, String key);
private native int valueSize(long handle, String key, boolean actualSize);

private static native void setLogLevel(int level);

private static native void setLogReDirecting(boolean enable);

private static native long createNB(int size);

private static native void destroyNB(long pointer, int size);

private native int writeValueToNB(long handle, String key, long pointer, int size);
}
Original file line number Diff line number Diff line change
Expand Up @@ -80,7 +80,9 @@ private static String queryAuthority(Context context) {
PackageManager mgr = context.getPackageManager();
if (mgr != null) {
ProviderInfo providerInfo = mgr.getProviderInfo(componentName, 0);
return providerInfo.authority;
if (providerInfo != null) {
return providerInfo.authority;
}
}
} catch (Exception e) {
e.printStackTrace();
Expand Down
11 changes: 11 additions & 0 deletions Android/MMKV/mmkv/src/main/java/com/tencent/mmkv/NativeBuffer.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
package com.tencent.mmkv;

public final class NativeBuffer {
public long pointer;
public int size;

public NativeBuffer(long ptr, int length) {
pointer = ptr;
size = length;
}
}
6 changes: 3 additions & 3 deletions Android/MMKV/mmkvdemo/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -57,14 +57,14 @@ repositories {
// }
jcenter()
mavenCentral()
mavenLocal()
// mavenLocal()
}

dependencies {
implementation fileTree(include: ['*.jar'], dir: 'libs')
// implementation project(':mmkv')
// implementation 'com.tencent:mmkv:1.0.17'
implementation 'com.tencent:mmkv-static:1.0.17'
implementation 'com.tencent:mmkv:1.0.18'
// implementation 'com.tencent:mmkv-static:1.0.18'
implementation 'com.android.support:appcompat-v7:28.0.0'
implementation 'com.android.support.constraint:constraint-layout:1.1.3'
testImplementation 'junit:junit:4.12'
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@
import com.tencent.mmkv.MMKVRecoverStrategic;
import com.tencent.mmkv.MMKVLogLevel;
import com.getkeepsafe.relinker.ReLinker;
import com.tencent.mmkv.NativeBuffer;

import org.jetbrains.annotations.Nullable;

Expand Down Expand Up @@ -200,7 +201,16 @@ private MMKV testMMKV(String mmapID, String cryptKey, boolean decodeOnly, String
byte[] bytes = kv.decodeBytes("bytes");
Log.i("MMKV", "bytes: " + new String(bytes));
Log.i("MMKV", "bytes length = " + bytes.length
+ ", value size consumption = " + kv.getValueSize("bytes"));
+ ", value size consumption = " + kv.getValueSize("bytes")
+ ", value size = " + kv.getValueActualSize("bytes"));

int sizeNeeded = kv.getValueActualSize("bytes");
NativeBuffer nativeBuffer = MMKV.createNativeBuffer(sizeNeeded);
if (nativeBuffer != null) {
int size = kv.writeValueToNativeBuffer("bytes", nativeBuffer);
Log.i("MMKV", "size Needed = " + sizeNeeded + " written size = " + size);
MMKV.destroyNativeBuffer(nativeBuffer);
}

if (!decodeOnly) {
TestParcelable testParcelable = new TestParcelable(1024, "Hi Parcelable");
Expand Down
Loading

0 comments on commit 87eaabe

Please sign in to comment.