@@ -79,7 +79,7 @@ static void wait_for_worker_startup(SpockWorker *worker,
7979 BackgroundWorkerHandle * handle );
8080static void signal_worker_xact_callback (XactEvent event , void * arg );
8181static uint32 spock_ch_stats_hash (const void * key , Size keysize );
82- static bool spock_shmem_init_internal (int nworkers );
82+ static void spock_shmem_init_internal (int nworkers );
8383
8484
8585void
@@ -344,15 +344,6 @@ spock_worker_on_exit(int code, Datum arg)
344344void
345345spock_worker_attach (int slot , SpockWorkerType type )
346346{
347- /*
348- * Ensure shared memory is attached before using SpockCtx.
349- *
350- * Background workers inherit global variables from the postmaster but the
351- * pointers may not be valid. Always call spock_shmem_attach() which is
352- * idempotent and handles proper re-initialization.
353- */
354- spock_shmem_attach ();
355-
356347 Assert (slot >= 0 );
357348 Assert (slot < SpockCtx -> total_workers );
358349
@@ -838,9 +829,18 @@ spock_worker_shmem_startup(void)
838829 * This is kludge for Windows (Postgres does not define the GUC variable
839830 * as PGDLLIMPORT)
840831 */
841- nworkers = atoi (GetConfigOptionByName ("max_worker_processes" , NULL ,
842- false));
832+ nworkers = atoi (GetConfigOptionByName ("max_worker_processes" , NULL , false));
833+
834+ /*
835+ * Reset in case this is a restart within the postmaster
836+ * Spock extension must be loaded on startup. In case of a fatal error and
837+ * further restart, postmaster clean up shared memory but local variables
838+ * stay the same. So, we need to clean outdated pointers in advance.
839+ */
843840 SpockCtx = NULL ;
841+ SpockHash = NULL ;
842+ SpockGroupHash = NULL ;
843+ exception_log_ptr = NULL ;
844844
845845 /* Avoid possible race-conditions when initializing shared memory. */
846846 LWLockAcquire (AddinShmemInitLock , LW_EXCLUSIVE );
@@ -850,7 +850,7 @@ spock_worker_shmem_startup(void)
850850 * This internally calls spock_group_shmem_startup() to handle group
851851 * initialization and file loading.
852852 */
853- ( void ) spock_shmem_init_internal (nworkers );
853+ spock_shmem_init_internal (nworkers );
854854
855855 LWLockRelease (AddinShmemInitLock );
856856}
@@ -878,70 +878,52 @@ spock_ch_stats_hash(const void *key, Size keysize)
878878 * This centralizes the logic for setting up all Spock shared memory pointers,
879879 * which is used by both the initial startup hook and the attach function.
880880 */
881- static bool
881+ static void
882882spock_shmem_init_internal (int nworkers )
883883{
884884 HASHCTL hctl ;
885885 bool found ;
886- bool all_found = true;
887-
888886
889887 /* Init signaling context for the various processes. */
890- if (!SpockCtx )
888+ SpockCtx = ShmemInitStruct ("spock_context" ,
889+ worker_shmem_size (nworkers , false), & found );
890+ if (!found )
891891 {
892- SpockCtx = ShmemInitStruct ("spock_context" ,
893- worker_shmem_size (nworkers , false), & found );
894- if (!SpockCtx )
895- elog (ERROR , "failed to initialize spock_context" );
896-
897- if (!found )
898- {
899- /* First time - initialize the structure */
900- SpockCtx -> lock = & ((GetNamedLWLockTranche ("spock" )[0 ]).lock );
901- SpockCtx -> apply_group_master_lock = & ((GetNamedLWLockTranche (SPOCK_GROUP_TRANCHE_NAME )[0 ]).lock );
902- SpockCtx -> supervisor = NULL ;
903- SpockCtx -> subscriptions_changed = false;
904- SpockCtx -> total_workers = nworkers ;
905- memset (SpockCtx -> workers , 0 ,
906- sizeof (SpockWorker ) * SpockCtx -> total_workers );
907- all_found = false;
908- }
892+ /* First time - initialize the structure */
893+ SpockCtx -> lock = & ((GetNamedLWLockTranche ("spock" )[0 ]).lock );
894+ SpockCtx -> apply_group_master_lock = & ((GetNamedLWLockTranche (SPOCK_GROUP_TRANCHE_NAME )[0 ]).lock );
895+ SpockCtx -> slot_group_master_lock = & ((GetNamedLWLockTranche ("spock_slot_groups" )[0 ]).lock );
896+ SpockCtx -> slot_ngroups = nworkers ;
897+ SpockCtx -> supervisor = NULL ;
898+ SpockCtx -> subscriptions_changed = false;
899+ SpockCtx -> total_workers = nworkers ;
900+ memset (SpockCtx -> workers , 0 ,
901+ sizeof (SpockWorker ) * SpockCtx -> total_workers );
909902 }
910903
911904 /*
912905 * Initialize exception log pointer array.
913906 */
914- if (!exception_log_ptr )
915- {
916- exception_log_ptr = ShmemInitStruct ("spock_exception_log_ptr" ,
917- worker_shmem_size (nworkers , false), & found );
918- if (!exception_log_ptr )
919- elog (ERROR , "failed to initialize spock_exception_log_ptr" );
907+ exception_log_ptr = ShmemInitStruct ("spock_exception_log_ptr" ,
908+ worker_shmem_size (nworkers , false), & found );
920909
921- if (!found )
922- {
923- memset (exception_log_ptr , 0 , sizeof (SpockExceptionLog ) * nworkers );
924- all_found = false;
925- }
910+ if (!found )
911+ {
912+ memset (exception_log_ptr , 0 , sizeof (SpockExceptionLog ) * nworkers );
926913 }
927914
928915 /*
929916 * Initialize SpockHash - channel stats hash.
930917 */
931- if (!SpockHash )
932- {
933- memset (& hctl , 0 , sizeof (hctl ));
934- hctl .keysize = sizeof (spockStatsKey );
935- hctl .entrysize = sizeof (spockStatsEntry );
936- hctl .hash = spock_ch_stats_hash ;
937- SpockHash = ShmemInitHash ("spock channel stats hash" ,
938- spock_stats_max_entries ,
939- spock_stats_max_entries ,
940- & hctl ,
941- HASH_ELEM | HASH_FUNCTION | HASH_FIXED_SIZE );
942- if (!SpockHash )
943- elog (ERROR , "failed to initialize spock channel stats hash" );
944- }
918+ memset (& hctl , 0 , sizeof (hctl ));
919+ hctl .keysize = sizeof (spockStatsKey );
920+ hctl .entrysize = sizeof (spockStatsEntry );
921+ hctl .hash = spock_ch_stats_hash ;
922+ SpockHash = ShmemInitHash ("spock channel stats hash" ,
923+ spock_stats_max_entries ,
924+ spock_stats_max_entries ,
925+ & hctl ,
926+ HASH_ELEM | HASH_FUNCTION | HASH_FIXED_SIZE );
945927
946928 /*
947929 * Initialize SpockGroupHash via the spock_group module. This handles both
@@ -950,68 +932,7 @@ spock_shmem_init_internal(int nworkers)
950932 * Note: We pass 'all_found' to indicate whether this is first-time setup
951933 * or attachment to existing structures.
952934 */
953- spock_group_shmem_startup (nworkers , all_found );
954-
955- return all_found ;
956- }
957-
958- /*
959- * spock_shmem_attach
960- *
961- * Attach (or re-attach) to existing shared memory structures.
962- *
963- * This is called from processes that need to access Spock's shared memory:
964- * - Startup process (via spock_rmgr_startup) - once per recovery
965- * - Checkpointer (via spock_checkpoint_hook) - once per process lifetime
966- * - Background workers (via spock_worker_attach) - once per worker
967- *
968- * IMPORTANT: Auxiliary processes (startup, checkpointer) inherit global
969- * variable values from the postmaster, but these pointers might not be valid
970- * in their address space.
971- *
972- * This function uses a static flag to ensure we only attach once per process,
973- * avoiding redundant shared memory lookups on subsequent calls.
974- *
975- * Unlike spock_worker_shmem_startup(), this doesn't acquire AddinShmemInitLock
976- * or register hooks - it just looks up and attaches to existing structures.
977- */
978- void
979- spock_shmem_attach (void )
980- {
981- static bool attached = false;
982- int nworkers ;
983-
984- /* If already attached in this process, nothing to do */
985- if (attached )
986- return ;
987-
988- /*
989- * Reset globals to NULL to force proper attachment.
990- *
991- * This is critical for auxiliary processes (startup, checkpointer) that
992- * inherit invalid global values from the postmaster.
993- */
994- SpockCtx = NULL ;
995- SpockHash = NULL ;
996- SpockGroupHash = NULL ;
997- exception_log_ptr = NULL ;
998-
999- /*
1000- * Get max_worker_processes to know the size of structures.
1001- */
1002- nworkers = atoi (GetConfigOptionByName ("max_worker_processes" , NULL , false));
1003- if (nworkers <= 0 )
1004- nworkers = 9 ;
1005-
1006- /*
1007- * Attach to all structures using the common initialization logic. Returns
1008- * true if structures were found (normal case), false if they had to be
1009- * created (shouldn't happen but harmless).
1010- */
1011- (void ) spock_shmem_init_internal (nworkers );
1012-
1013- /* Mark as attached to avoid redundant work on subsequent calls */
1014- attached = true;
935+ spock_group_shmem_startup (nworkers );
1015936}
1016937
1017938/*
0 commit comments