File: ss_context_mgr.c

package info (click to toggle)
fis-gtm 7.1-006-1
  • links: PTS, VCS
  • area: main
  • in suites: trixie
  • size: 32,908 kB
  • sloc: ansic: 344,906; asm: 5,184; csh: 4,859; sh: 2,000; awk: 294; makefile: 73; sed: 13
file content (180 lines) | stat: -rw-r--r-- 5,856 bytes parent folder | download | duplicates (3)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
/****************************************************************
 *								*
 * Copyright (c) 2009-2021 Fidelity National Information	*
 * Services, Inc. and/or its subsidiaries. All rights reserved.	*
 *								*
 *	This source code contains the intellectual property	*
 *	of its copyright holder(s), and is made available	*
 *	under a license.  If you do not know the terms of	*
 *	the license, please stop and do not read further.	*
 *								*
 ****************************************************************/
#include "mdef.h"

#include "gtm_fcntl.h"
#include "gtm_stat.h"
#include "gtm_unistd.h"
#include <sys/mman.h>
#include <sys/shm.h>
#include "gtm_permissions.h"
#include "gtm_string.h"
#include "gtm_stdio.h"
#include "gtm_stdlib.h"
#include "gtm_tempnam.h"
#include "gtm_time.h"
#ifdef DEBUG
#include "gtm_ipc.h"
#endif

#include "gdsroot.h"
#include "gdskill.h"
#include "gtm_facility.h"
#include "fileinfo.h"
#include "gdsbt.h"
#include "gdsblk.h"
#include "gdsfhead.h"
#include "filestruct.h"
#include "iosp.h"
#include "error.h"
#include "cli.h"
#include "eintr_wrappers.h"
#include "gtmio.h"
#include "repl_sp.h"
#include "gtm_file_stat.h"
#include "util.h"
#include "gtm_caseconv.h"
#include "gt_timer.h"
#include "is_proc_alive.h"
#include "is_file_identical.h"
#include "dbfilop.h"
#include "wcs_flu.h"
#include "jnl.h"
#include "interlock.h"
#include "sleep_cnt.h"
#include "mupip_exit.h"
#include "trans_log_name.h"
#include "gtmimagename.h"
#include "send_msg.h"
#include "gtm_logicals.h"
#include "memcoherency.h"
#ifdef __MVS__
#include "gtm_zos_io.h"
#endif
#include "shmpool.h"
#include "db_snapshot.h"
#include "do_shmat.h"

GBLREF	sgmnt_addrs		*cs_addrs;
GBLREF	enum gtmImageTypes	image_type;
GBLREF	uint4			process_id;

error_def(ERR_SYSCALL);

boolean_t	ss_create_context(snapshot_context_ptr_t lcl_ss_ctx, int ss_shmcycle)
{
	shm_snapshot_ptr_t		ss_shm_ptr;
	node_local_ptr_t		cnl;
	sgmnt_addrs			*csa;
	int				shdw_fd, status;
	void				*ss_shmaddr;
	ZOS_ONLY(int			realfiletag;)

	ZOS_ONLY(error_def(ERR_BADTAG);)
	ZOS_ONLY(error_def(ERR_TEXT);)

	assert(NULL != cs_addrs);
	csa = cs_addrs;
	cnl = csa->nl;

	ss_destroy_context(lcl_ss_ctx); /* Before creating a new one relinquish the existing one */
	lcl_ss_ctx->ss_shmcycle = ss_shmcycle;
	/* SS_MULTI: In case of multiple snapshots, we can't assume that the first index of the snapshot structure in the db
	 * shared memory is the currently active snapshot.
	 */
	assert(1 == MAX_SNAPSHOTS); /* This assert will fail when we increase the MAX_SNAPSHOTS per region */
	ss_shm_ptr = (shm_snapshot_ptr_t)SS_GETSTARTPTR(csa);
	DBG_ENSURE_PTR_WITHIN_SS_BOUNDS(csa, (sm_uc_ptr_t)ss_shm_ptr);
	/* The below memory barrier will ensure that if ever the shmcycle is modified in ss_initiate, we get the up to date
	 * values of the other members in the snapshot structure (copied below).
	 */
	SHM_READ_MEMORY_BARRIER;
	STRCPY(lcl_ss_ctx->shadow_file, ss_shm_ptr->ss_info.shadow_file);
	lcl_ss_ctx->total_blks = ss_shm_ptr->ss_info.total_blks;
	lcl_ss_ctx->shadow_vbn = ss_shm_ptr->ss_info.shadow_vbn;
	lcl_ss_ctx->ss_shm_ptr = ss_shm_ptr;
	lcl_ss_ctx->nl_shmid = cnl->ss_shmid;
	/* Attach to the shared memory created by snapshot */
	if (INVALID_SHMID != lcl_ss_ctx->nl_shmid)
	{
		if (-1 == (sm_long_t)(ss_shmaddr = do_shmat(lcl_ss_ctx->nl_shmid, 0, 0)))
		{
			status = errno;
			/* It's possible that by the time we attach to the shared memory, the identifier has been removed from the
			 * system by INTEG which completed it's processing.
			 */
			assert(SHM_REMOVED(status));
			assert(INVALID_SHMID == lcl_ss_ctx->attach_shmid);
			lcl_ss_ctx->cur_state = SNAPSHOT_SHM_ATTACH_FAIL;
			lcl_ss_ctx->failure_errno = status;
			return FALSE;
		}
		lcl_ss_ctx->attach_shmid = lcl_ss_ctx->nl_shmid;
		lcl_ss_ctx->start_shmaddr = (sm_uc_ptr_t)ss_shmaddr;
		lcl_ss_ctx->bitmap_addr = ((sm_uc_ptr_t)ss_shmaddr + SNAPSHOT_HDR_SIZE);
	} else
	{	/* No ongoing snapshots. Do early return. t_end and tp_tend during validation will identify this change in state
		 * and will turn off snapshot activities
		 */
		lcl_ss_ctx->start_shmaddr = NULL;
		lcl_ss_ctx->bitmap_addr = NULL;
		lcl_ss_ctx->cur_state = SNAPSHOT_NOT_INITED;
		return FALSE;
	}
	OPENFILE(lcl_ss_ctx->shadow_file, O_RDWR, shdw_fd);
	lcl_ss_ctx->shdw_fd = shdw_fd;
	if (FD_INVALID == shdw_fd)
	{
		assert((NULL != ss_shmaddr)
			&& (-1 != lcl_ss_ctx->attach_shmid)); /* shared memory attach SHOULD have succeeded */
		if (-1 == SHMDT(ss_shmaddr))
		{
			status = errno;
			assert(FALSE);
			RTS_ERROR_CSA_ABT(NULL, VARLSTCNT(8) ERR_SYSCALL, 5, LEN_AND_LIT("Error with shmdt"), CALLFROM, status);
		}
		lcl_ss_ctx->attach_shmid = lcl_ss_ctx->nl_shmid = INVALID_SHMID; /* reset shmid since we failed */
		lcl_ss_ctx->cur_state = SHADOW_FIL_OPEN_FAIL;
		lcl_ss_ctx->failure_errno = errno;
		return FALSE;
	}
#	ifdef __MVS__
	if (-1 == gtm_zos_tag_to_policy(shdw_fd, TAG_BINARY, &realfiletag))
		TAG_POLICY_SEND_MSG(ss_shm_ptr->ss_info.shadow_file, errno, realfiletag, TAG_BINARY);
#	endif
	lcl_ss_ctx->cur_state = SNAPSHOT_INIT_DONE;
	return TRUE;
}

boolean_t	ss_destroy_context(snapshot_context_ptr_t lcl_ss_ctx)
{
	int				status;

	assert(NULL != lcl_ss_ctx);
	if (FD_INVALID != lcl_ss_ctx->shdw_fd)
	{
		CLOSEFILE_RESET(lcl_ss_ctx->shdw_fd, status);
	}
#	ifdef DEBUG
	if (gtm_white_box_test_case_enabled && (WBTEST_FAKE_SS_SHMDT_WINDOW == gtm_white_box_test_case_number))
	{
		FPRINTF(stdout, "About to delete shm at %x\n", lcl_ss_ctx->start_shmaddr);
		if (INVALID_SHMID == lcl_ss_ctx->attach_shmid)
			lcl_ss_ctx->attach_shmid = 0 ;	/* ensure / fake that it's not invalid */
	}
#	endif
	if (INVALID_SHMID != lcl_ss_ctx->attach_shmid)
		SHMDT((void *)(lcl_ss_ctx->start_shmaddr));	/* no check for errors that 'cause gone is the goal */
	/* Invalidate the context */
	DEFAULT_INIT_SS_CTX(lcl_ss_ctx);
	return TRUE;
}