/* since linux-3.5, kernel supports to set the state of the "THP disable" flag
* for the calling thread. PR_SET_THP_DISABLE is defined in linux/prctl.h */
staticintTHPDisable(void){
intret=-EINVAL;
if(!fp)return-1;
if(fgets(buf,64,fp)==NULL){
fclose(fp);
return-1;
}
fclose(fp);
if(!server.disable_thp)
returnret;
returnatoi(buf);
#ifdef PR_SET_THP_DISABLE
ret=prctl(PR_SET_THP_DISABLE,1,0,0,0);
#endif
returnret;
}
voidlinuxMemoryWarnings(void){
if(linuxOvercommitMemoryValue()==0){
serverLog(LL_WARNING,"WARNING overcommit_memory is set to 0! Background save may fail under low memory condition. To fix this issue add 'vm.overcommit_memory = 1' to /etc/sysctl.conf and then reboot or run the command 'sysctl vm.overcommit_memory=1' for this to take effect.");
sdserr_msg;
if(checkOvercommit(&err_msg)<0){
serverLog(LL_WARNING,"WARNING %s",err_msg);
sdsfree(err_msg);
}
if(THPIsEnabled()){
if(checkTHPEnabled(&err_msg)<0){
server.thp_enabled=1;
if(THPDisable()==0){
server.thp_enabled=0;
return;
}
serverLog(LL_WARNING,"WARNING you have Transparent Huge Pages (THP) support enabled in your kernel. This will create latency and memory usage issues with Redis. To fix this issue run the command 'echo madvise > /sys/kernel/mm/transparent_hugepage/enabled' as root, and add it to your /etc/rc.local in order to retain the setting after a reboot. Redis must be restarted after THP is disabled (set to 'madvise' or 'never').");
}
}
#ifdef __arm64__
/* Get size in kilobytes of the Shared_Dirty pages of the calling process for the
* memory map corresponding to the provided address, or -1 on error. */
staticintsmapsGetSharedDirty(unsignedlongaddr){
intret,in_mapping=0,val=-1;
unsignedlongfrom,to;
charbuf[64];
FILE*f;
f=fopen("/proc/self/smaps","r");
if(!f)return-1;
while(1){
if(!fgets(buf,sizeof(buf),f))
break;
ret=sscanf(buf,"%lx-%lx",&from,&to);
if(ret==2)
in_mapping=from<=addr&&addr<to;
if(in_mapping&&!memcmp(buf,"Shared_Dirty:",13)){
sscanf(buf,"%*s %d",&val);
/* If parsing fails, we remain with val == -1 */
break;
}
}
fclose(f);
returnval;
}
/* Older arm64 Linux kernels have a bug that could lead to data corruption
* during background save in certain scenarios. This function checks if the
* kernel is affected.
* The bug was fixed in commit ff1712f953e27f0b0718762ec17d0adb15c9fd0b
* titled: "arm64: pgtable: Ensure dirty bit is preserved across pte_wrprotect()"
* Return -1 on unexpected test failure, 1 if the kernel seems to be affected,
* and 0 otherwise. */
intlinuxMadvFreeForkBugCheck(void){
intret,pipefd[2]={-1,-1};
pid_tpid;
char*p=NULL,*q;
intbug_found=0;
longpage_size=sysconf(_SC_PAGESIZE);
longmap_size=3*page_size;
/* Create a memory map that's in our full control (not one used by the allocator). */