diff --git a/buildNumber.properties b/buildNumber.properties index d9e60052..ddb10881 100644 --- a/buildNumber.properties +++ b/buildNumber.properties @@ -1,3 +1,3 @@ #maven.buildNumber.plugin properties file -#Sun Dec 01 15:41:36 EST 2024 -buildNumber=471 +#Sun Dec 01 15:59:03 EST 2024 +buildNumber=475 diff --git a/docs/src/progress/renderertodo.md b/docs/src/progress/renderertodo.md index 505ae1d8..b7a19d94 100644 --- a/docs/src/progress/renderertodo.md +++ b/docs/src/progress/renderertodo.md @@ -1208,6 +1208,7 @@ Remove conditional update check in fluid sim Explicit memory management of fluid chunk cache buffers Fix GriddedDataCellManager memory leak caused by physics and ConcurrentHashMap Fix fluid sim null pointer bug with unallocated chunks +Fix fluid sim NP bug with skipped chunks diff --git a/src/fluid/src/javainterface.c b/src/fluid/src/javainterface.c index 984e8ff1..0938baf7 100644 --- a/src/fluid/src/javainterface.c +++ b/src/fluid/src/javainterface.c @@ -20,12 +20,11 @@ #define getChunk(i) (*env)->CallObjectMethod(env,chunkList,jListGet,i) #define getBuffArr(buffId) (*env)->GetObjectField(env,chunkJRaw,buffId) #define setBuffArr(buffId,value) (*env)->SetObjectField(env,chunkJRaw,buffId,value) -#define GET_ARR(env,src,i) (*env)->GetDirectBufferAddress(env,(*env)->GetObjectArrayElement(env,src,i)) //declarations -void readInChunks(JNIEnv * env, jobject chunkList, Environment * environment); +int readInChunks(JNIEnv * env, jobject chunkList, Environment * environment); int calculateChunkMask(JNIEnv * env, jobjectArray jrx); uint32_t matrix_transform(JNIEnv * env, jobjectArray jrx); @@ -40,15 +39,22 @@ int numChunks = 0; Environment * environment = NULL; + +/** + * Gets the array pointer + */ +void * getArray(JNIEnv * env, jobjectArray arr, int index); + + JNIEXPORT void JNICALL Java_electrosphere_server_fluid_simulator_FluidAcceleratedSimulator_simulate( JNIEnv * env, jclass fluidSimClass, jobject chunkList, jfloat dt ){ - readInChunks(env,chunkList,environment); - simulate(numChunks,chunkViewC,environment,dt); - updateMetadata(env,numChunks,chunkViewC,environment); + int numReadIn = readInChunks(env,chunkList,environment); + simulate(numReadIn,chunkViewC,environment,dt); + updateMetadata(env,numReadIn,chunkViewC,environment); } /** @@ -111,8 +117,9 @@ JNIEXPORT void JNICALL Java_electrosphere_server_fluid_simulator_FluidAccelerate /** * Reads chunks into the dynamic array + * @return The number of chunks that were successfully parsed */ -void readInChunks(JNIEnv * env, jobject chunkList, Environment * environment){ +int readInChunks(JNIEnv * env, jobject chunkList, Environment * environment){ jclass listClass = (*env)->FindClass(env,"java/util/List"); jclass fluidSimClass = (*env)->FindClass(env,"electrosphere/server/fluid/manager/ServerFluidChunk"); //JNIEnv *env, jclass clazz, const char *name, const char *sig @@ -151,17 +158,20 @@ void readInChunks(JNIEnv * env, jobject chunkList, Environment * environment){ int cSideArrPos = 0; for(int i = 0; i < numChunks; i++){ chunkJRaw = getChunk(i); - chunkMask = calculateChunkMask(env,getBuffArr(dJId)); - (*env)->SetIntField(env,chunkJRaw,chunkmaskJId,chunkMask); //skip this chunk if the center array is not allocated (must not have been removed yet?) if( - (*env)->GetObjectArrayElement(env,(*env)->GetObjectField(env,chunkJRaw,dJId),CENTER_LOC) == NULL || - (*env)->GetDirectBufferAddress(env,(*env)->GetObjectArrayElement(env,(*env)->GetObjectField(env,chunkJRaw,dJId),CENTER_LOC)) == NULL + getBuffArr(dJId) == NULL || + (*env)->GetObjectArrayElement(env,getBuffArr(dJId),CENTER_LOC) == NULL || + (*env)->GetDirectBufferAddress(env,(*env)->GetObjectArrayElement(env,getBuffArr(dJId),CENTER_LOC)) == NULL ){ continue; } + //calculate chunk mask + chunkMask = calculateChunkMask(env,getBuffArr(dJId)); + (*env)->SetIntField(env,chunkJRaw,chunkmaskJId,chunkMask); + Chunk * newChunk; if(cSideArrPos >= stbds_arrlen(chunkViewC)){ // printf("allocate chunk %d\n",i); @@ -190,19 +200,30 @@ void readInChunks(JNIEnv * env, jobject chunkList, Environment * environment){ newChunk->chunkJRaw = chunkJRaw; for(int j = 0; j < 27; j++){ if((chunkMask & CHUNK_INDEX_ARR[j]) > 0){ - newChunk->d[j] = GET_ARR(env,jd,j); - newChunk->d0[j] = GET_ARR(env,jd0,j); - newChunk->u[j] = GET_ARR(env,u,j); - newChunk->v[j] = GET_ARR(env,v,j); - newChunk->w[j] = GET_ARR(env,w,j); - newChunk->u0[j] = GET_ARR(env,u0,j); - newChunk->v0[j] = GET_ARR(env,v0,j); - newChunk->w0[j] = GET_ARR(env,w0,j); + newChunk->d[j] = getArray(env,jd,j); + newChunk->d0[j] = getArray(env,jd0,j); + newChunk->u[j] = getArray(env,u,j); + newChunk->v[j] = getArray(env,v,j); + newChunk->w[j] = getArray(env,w,j); + newChunk->u0[j] = getArray(env,u0,j); + newChunk->v0[j] = getArray(env,v0,j); + newChunk->w0[j] = getArray(env,w0,j); } } } + return cSideArrPos; } +/** + * Gets the array pointer + */ +void * getArray(JNIEnv * env, jobjectArray arr, int index){ + jobject arrayEl = (*env)->GetObjectArrayElement(env,arr,index); + if(arrayEl == NULL){ + return NULL; + } + return (*env)->GetDirectBufferAddress(env,arrayEl); +} /** * Calculates the bitmask for available chunks for the provided chunk's neighbor array