Called when the user switches from "appendonly no" to "appendonly yes" * at runtime using the CONFIG command. */
| 269 | /* Called when the user switches from "appendonly no" to "appendonly yes" |
| 270 | * at runtime using the CONFIG command. */ |
| 271 | int startAppendOnly(void) { |
| 272 | char cwd[MAXPATHLEN]; /* Current working dir path for error messages. */ |
| 273 | int newfd; |
| 274 | |
| 275 | newfd = open(g_pserver->aof_filename,O_WRONLY|O_APPEND|O_CREAT,0644); |
| 276 | serverAssert(g_pserver->aof_state == AOF_OFF); |
| 277 | if (newfd == -1) { |
| 278 | char *cwdp = getcwd(cwd,MAXPATHLEN); |
| 279 | |
| 280 | serverLog(LL_WARNING, |
| 281 | "KeyDB needs to enable the AOF but can't open the " |
| 282 | "append only file %s (in server root dir %s): %s", |
| 283 | g_pserver->aof_filename, |
| 284 | cwdp ? cwdp : "unknown", |
| 285 | strerror(errno)); |
| 286 | return C_ERR; |
| 287 | } |
| 288 | if (hasActiveChildProcessOrBGSave() && g_pserver->child_type != CHILD_TYPE_AOF) { |
| 289 | g_pserver->aof_rewrite_scheduled = 1; |
| 290 | serverLog(LL_WARNING,"AOF was enabled but there is already another background operation. An AOF background was scheduled to start when possible."); |
| 291 | } else { |
| 292 | /* If there is a pending AOF rewrite, we need to switch it off and |
| 293 | * start a new one: the old one cannot be reused because it is not |
| 294 | * accumulating the AOF buffer. */ |
| 295 | if (g_pserver->child_type == CHILD_TYPE_AOF) { |
| 296 | serverLog(LL_WARNING,"AOF was enabled but there is already an AOF rewriting in background. Stopping background AOF and starting a rewrite now."); |
| 297 | killAppendOnlyChild(); |
| 298 | } |
| 299 | if (rewriteAppendOnlyFileBackground() == C_ERR) { |
| 300 | close(newfd); |
| 301 | serverLog(LL_WARNING,"KeyDB needs to enable the AOF but can't trigger a background AOF rewrite operation. Check the above logs for more info about the error."); |
| 302 | return C_ERR; |
| 303 | } |
| 304 | } |
| 305 | /* We correctly switched on AOF, now wait for the rewrite to be complete |
| 306 | * in order to append data on disk. */ |
| 307 | g_pserver->aof_state = AOF_WAIT_REWRITE; |
| 308 | g_pserver->aof_last_fsync = g_pserver->unixtime; |
| 309 | g_pserver->aof_fd = newfd; |
| 310 | |
| 311 | /* If AOF fsync error in bio job, we just ignore it and log the event. */ |
| 312 | int aof_bio_fsync_status; |
| 313 | atomicGet(g_pserver->aof_bio_fsync_status, aof_bio_fsync_status); |
| 314 | if (aof_bio_fsync_status == C_ERR) { |
| 315 | serverLog(LL_WARNING, |
| 316 | "AOF reopen, just ignore the AOF fsync error in bio job"); |
| 317 | atomicSet(g_pserver->aof_bio_fsync_status,C_OK); |
| 318 | } |
| 319 | |
| 320 | /* If AOF was in error state, we just ignore it and log the event. */ |
| 321 | if (g_pserver->aof_last_write_status == C_ERR) { |
| 322 | serverLog(LL_WARNING,"AOF reopen, just ignore the last error."); |
| 323 | g_pserver->aof_last_write_status = C_OK; |
| 324 | } |
| 325 | return C_OK; |
| 326 | } |
| 327 | |
| 328 | /* This is a wrapper to the write syscall in order to retry on short writes |
no test coverage detected