| 1199 | # endif |
| 1200 | #endif |
| 1201 | void serverLogRaw(int level, const char *msg) { |
| 1202 | const int syslogLevelMap[] = { LOG_DEBUG, LOG_INFO, LOG_NOTICE, LOG_WARNING }; |
| 1203 | const char *c = ".-*# "; |
| 1204 | FILE *fp; |
| 1205 | char buf[64]; |
| 1206 | int rawmode = (level & LL_RAW); |
| 1207 | int log_to_stdout = g_pserver->logfile[0] == '\0'; |
| 1208 | |
| 1209 | level &= 0xff; /* clear flags */ |
| 1210 | if (level < cserver.verbosity) return; |
| 1211 | |
| 1212 | fp = log_to_stdout ? stdout : fopen(g_pserver->logfile,"a"); |
| 1213 | if (!fp) return; |
| 1214 | |
| 1215 | if (rawmode) { |
| 1216 | fprintf(fp,"%s",msg); |
| 1217 | } else { |
| 1218 | int off; |
| 1219 | struct timeval tv; |
| 1220 | int role_char; |
| 1221 | pid_t pid = getpid(); |
| 1222 | |
| 1223 | gettimeofday(&tv,NULL); |
| 1224 | struct tm tm; |
| 1225 | int daylight_active; |
| 1226 | __atomic_load(&g_pserver->daylight_active, &daylight_active, __ATOMIC_RELAXED); |
| 1227 | nolocks_localtime(&tm,tv.tv_sec,g_pserver->timezone,daylight_active); |
| 1228 | off = strftime(buf,sizeof(buf),"%d %b %Y %H:%M:%S.",&tm); |
| 1229 | snprintf(buf+off,sizeof(buf)-off,"%03d",(int)tv.tv_usec/1000); |
| 1230 | if (g_pserver->sentinel_mode) { |
| 1231 | role_char = 'X'; /* Sentinel. */ |
| 1232 | } else if (pid != cserver.pid) { |
| 1233 | role_char = 'C'; /* RDB / AOF writing child. */ |
| 1234 | } else { |
| 1235 | role_char = (listLength(g_pserver->masters) ? 'S':'M'); /* Slave or Master. */ |
| 1236 | } |
| 1237 | fprintf(fp,"%d:%d:%c %s %c %s\n", |
| 1238 | (int)getpid(),(int)gettid(),role_char, buf,c[level],msg); |
| 1239 | } |
| 1240 | fflush(fp); |
| 1241 | |
| 1242 | if (!log_to_stdout) fclose(fp); |
| 1243 | if (g_pserver->syslog_enabled) syslog(syslogLevelMap[level], "%s", msg); |
| 1244 | } |
| 1245 | |
| 1246 | /* Like serverLogRaw() but with printf-alike support. This is the function that |
| 1247 | * is used across the code. The raw version is only used in order to dump |
no test coverage detected