DATA_BLOCK DB 99
STRUCT
	VAR0	: INT := 111;
	VAR10	: STRUCT
		VAR10_1		: INT  := 101;
		VAR10_2		: ARRAY  [1 .. 2 ] OF INT  := 1, 2;
		VAR10_3		: ARRAY  [1 .. 2 ] OF STRUCT
			VAR10_3_1	: INT  := 1031;
			VAR10_3_2	: ARRAY  [1 .. 2 ] OF INT  := 1, 2;
		END_STRUCT;
		VAR10_4		: INT;
	END_STRUCT;
	VAR20	: ARRAY [4 .. 5] OF STRUCT
		VAR20_1		: WORD;
	END_STRUCT
	VAR1	: DWORD;
END_STRUCT;
BEGIN
	VAR0				:= 10101;
	VAR10.VAR10_1			:= 101;
	VAR10.VAR10_2[1]		:= 1;
	VAR10.VAR10_2[2]		:= 2;
//	VAR10.VAR10_3[1].VAR10_3_1	:= 1031;
//	VAR10.VAR10_3[1].VAR10_3_2[1]	:= 1;
//	VAR10.VAR10_3[1].VAR10_3_2[2]	:= 2;
	VAR10.VAR10_3[2].VAR10_3_1	:= 1032;
	VAR10.VAR10_3[2].VAR10_3_2[1]	:= 3;
	VAR10.VAR10_3[2].VAR10_3_2[2]	:= 4;
	VAR10.VAR10_4			:= 104;
	VAR20[4].VAR20_1		:= W#16#204;
	VAR20[5].VAR20_1		:= W#16#205;
	VAR1				:= DW#16#111;
END_DATA_BLOCK


FUNCTION_BLOCK FB 1
VAR_INPUT
	FBVAR0		: DINT;
	FBVAR1		: STRUCT
		FBVAR1_1	: INT;
		FBVAR1_2	: DINT;
		FBVAR1_3	: STRUCT
			FBVAR1_3_1	: INT;
			FBVAR1_3_2	: INT;
		END_STRUCT;
	END_STRUCT;
	FBVAR2		: ARRAY [1 .. 2] OF STRUCT
		FBVAR2_1	: DWORD;
		FBVAR2_2	: ARRAY [1 .. 2] OF WORD;
	END_STRUCT;
END_VAR
VAR_TEMP
	FBTMP0		: STRUCT
		FBTMP0_1	: INT;
		FBTMP0_2	: DINT;
	END_STRUCT;
END_VAR
BEGIN
	// Check input variables
	L		#FBVAR0
	__ASSERT==	__ACCU 1,	L#9100
	L		#FBVAR1.FBVAR1_1
	__ASSERT==	__ACCU 1,	9101
	L		#FBVAR1.FBVAR1_2
	__ASSERT==	__ACCU 1,	L#9102
	L		#FBVAR1.FBVAR1_3.FBVAR1_3_1
	__ASSERT==	__ACCU 1,	9103
	L		#FBVAR1.FBVAR1_3.FBVAR1_3_2
	__ASSERT==	__ACCU 1,	9104
	L		#FBVAR2[1].FBVAR2_1
	__ASSERT==	__ACCU 1,	DW#16#9105
	L		#FBVAR2[1].FBVAR2_2[1]
	__ASSERT==	__ACCU 1,	W#16#9106
	L		#FBVAR2[1].FBVAR2_2[2]
	__ASSERT==	__ACCU 1,	W#16#9107
	L		#FBVAR2[2].FBVAR2_1
	__ASSERT==	__ACCU 1,	DW#16#9108
	L		#FBVAR2[2].FBVAR2_2[1]
	__ASSERT==	__ACCU 1,	W#16#9109
	L		#FBVAR2[2].FBVAR2_2[2]
	__ASSERT==	__ACCU 1,	W#16#9110


	// Check TEMP variables
	L		11
	T		#FBTMP0.FBTMP0_1
	L		L#111
	T		#FBTMP0.FBTMP0_2

	L		#FBTMP0.FBTMP0_1
	__ASSERT==	__ACCU 1,	11
	L		#FBTMP0.FBTMP0_2
	__ASSERT==	__ACCU 1,	111
END_FUNCTION_BLOCK


DATA_BLOCK DB 1
	FB 1
BEGIN
	FBVAR0				:= L#100;
	FBVAR1.FBVAR1_1			:= 101;
	FBVAR1.FBVAR1_2			:= L#102;
	FBVAR1.FBVAR1_3.FBVAR1_3_1	:= 103;
	FBVAR1.FBVAR1_3.FBVAR1_3_2	:= 104;
	FBVAR2[1].FBVAR2_1		:= DW#16#105;
	FBVAR2[1].FBVAR2_2[1]		:= W#16#106;
	FBVAR2[1].FBVAR2_2[2]		:= W#16#107;
	FBVAR2[2].FBVAR2_1		:= DW#16#108;
	FBVAR2[2].FBVAR2_2[1]		:= W#16#109;
	FBVAR2[2].FBVAR2_2[2]		:= W#16#110;
END_DATA_BLOCK


FUNCTION FC 1 : VOID
VAR_INPUT
	FCVAR0		: DINT;
	FCVAR1		: STRUCT
		FCVAR1_1	: INT;
		FCVAR1_2	: DINT;
		FCVAR1_3	: STRUCT
			FCVAR1_3_1	: INT;
			FCVAR1_3_2	: INT;
		END_STRUCT;
	END_STRUCT;
	FCVAR2		: ARRAY [1 .. 2] OF STRUCT
		FCVAR2_1	: DWORD;
		FCVAR2_2	: ARRAY [1 .. 2] OF WORD;
	END_STRUCT;
END_VAR
VAR_TEMP
	FCTMP0		: STRUCT
		FCTMP0_1	: INT;
		FCTMP0_2	: DINT;
	END_STRUCT;
END_VAR
BEGIN
	// Check input variables
	L		#FCVAR0
	__ASSERT==	__ACCU 1,	L#9100
	L		#FCVAR1.FCVAR1_1
	__ASSERT==	__ACCU 1,	9101
	L		#FCVAR1.FCVAR1_2
	__ASSERT==	__ACCU 1,	L#9102
	L		#FCVAR1.FCVAR1_3.FCVAR1_3_1
	__ASSERT==	__ACCU 1,	9103
	L		#FCVAR1.FCVAR1_3.FCVAR1_3_2
	__ASSERT==	__ACCU 1,	9104
	L		#FCVAR2[1].FCVAR2_1
	__ASSERT==	__ACCU 1,	DW#16#9105
	L		#FCVAR2[1].FCVAR2_2[1]
	__ASSERT==	__ACCU 1,	W#16#9106
	L		#FCVAR2[1].FCVAR2_2[2]
	__ASSERT==	__ACCU 1,	W#16#9107
	L		#FCVAR2[2].FCVAR2_1
	__ASSERT==	__ACCU 1,	DW#16#9108
	L		#FCVAR2[2].FCVAR2_2[1]
	__ASSERT==	__ACCU 1,	W#16#9109
	L		#FCVAR2[2].FCVAR2_2[2]
	__ASSERT==	__ACCU 1,	W#16#9110


	// Check TEMP variables
	L		11
	T		#FCTMP0.FCTMP0_1
	L		L#111
	T		#FCTMP0.FCTMP0_2

	L		#FCTMP0.FCTMP0_1
	__ASSERT==	__ACCU 1,	11
	L		#FCTMP0.FCTMP0_2
	__ASSERT==	__ACCU 1,	111
END_FUNCTION


// Data block for FC 1 / FB 1 parameter passing.
DATA_BLOCK DB 10
STRUCT
	DBVAR0		: DINT;
	DBVAR1		: STRUCT
		DBVAR1_1	: INT;
		DBVAR1_2	: DINT;
		DBVAR1_3	: STRUCT
			DBVAR1_3_1	: INT;
			DBVAR1_3_2	: INT;
		END_STRUCT;
	END_STRUCT;
	DBVAR2		: ARRAY [1 .. 2] OF STRUCT
		DBVAR2_1	: DWORD;
		DBVAR2_2	: ARRAY [1 .. 2] OF WORD;
	END_STRUCT;
END_STRUCT;
BEGIN
	DBVAR0				:= L#9100;
	DBVAR1.DBVAR1_1			:= 9101;
	DBVAR1.DBVAR1_2			:= L#9102;
	DBVAR1.DBVAR1_3.DBVAR1_3_1	:= 9103;
	DBVAR1.DBVAR1_3.DBVAR1_3_2	:= 9104;
	DBVAR2[1].DBVAR2_1		:= DW#16#9105;
	DBVAR2[1].DBVAR2_2[1]		:= W#16#9106;
	DBVAR2[1].DBVAR2_2[2]		:= W#16#9107;
	DBVAR2[2].DBVAR2_1		:= DW#16#9108;
	DBVAR2[2].DBVAR2_2[1]		:= W#16#9109;
	DBVAR2[2].DBVAR2_2[2]		:= W#16#9110;
END_DATA_BLOCK


ORGANIZATION_BLOCK OB 1
BEGIN
	// Check the DB 99 initial values.
	AUF		DB 99
	L		DBLG
	__ASSERT==	__ACCU 1,	30
	L		DBW 0	// DB99.VAR0
	__ASSERT==	__ACCU 1,	10101
	L		DBW 2	// DB99.VAR10.VAR10_1
	__ASSERT==	__ACCU 1,	101
	L		DBW 4	// DB99.VAR10.VAR10_2[1]
	__ASSERT==	__ACCU 1,	1
	L		DBW 6	// DB99.VAR10.VAR10_2[2]
	__ASSERT==	__ACCU 1,	2
	L		DBW 8	// DB99.VAR10.VAR10_3[1].VAR10_3_1
	__ASSERT==	__ACCU 1,	1031
	L		DBW 10	// DB99.VAR10.VAR10_3[1].VAR10_3_2[1]
	__ASSERT==	__ACCU 1,	1
	L		DBW 12	// DB99.VAR10.VAR10_3[1].VAR10_3_2[2]
	__ASSERT==	__ACCU 1,	2
	L		DBW 14	// DB99.VAR10.VAR10_3[2].VAR10_3_1
	__ASSERT==	__ACCU 1,	1032
	L		DBW 16	// DB99.VAR10.VAR10_3[2].VAR10_3_2[1]
	__ASSERT==	__ACCU 1,	3
	L		DBW 18	// DB99.VAR10.VAR10_3[2].VAR10_3_2[2]
	__ASSERT==	__ACCU 1,	4
	L		DBW 20	// DB99.VAR10.VAR10_4
	__ASSERT==	__ACCU 1,	104
	L		DBW 22	// DB99.VAR20[4].VAR20_1
	__ASSERT==	__ACCU 1,	W#16#204
	L		DBW 24	// DB99.VAR20[5].VAR20_1
	__ASSERT==	__ACCU 1,	W#16#205
	L		DBD 26	// DB99.VAR1
	__ASSERT==	__ACCU 1,	DW#16#111


	// Check symbolic DB 99 access.
	L		DB99.VAR0
	__ASSERT==	__ACCU 1,	10101
	L		DB99.VAR10.VAR10_1
	__ASSERT==	__ACCU 1,	101
	L		DB99.VAR10.VAR10_2[1]
	__ASSERT==	__ACCU 1,	1
	L		DB99.VAR10.VAR10_2[2]
	__ASSERT==	__ACCU 1,	2
	L		DB99.VAR10.VAR10_3[1].VAR10_3_1
	__ASSERT==	__ACCU 1,	1031
	L		DB99.VAR10.VAR10_3[1].VAR10_3_2[1]
	__ASSERT==	__ACCU 1,	1
	L		DB99.VAR10.VAR10_3[1].VAR10_3_2[2]
	__ASSERT==	__ACCU 1,	2
	L		DB99.VAR10.VAR10_3[2].VAR10_3_1
	__ASSERT==	__ACCU 1,	1032
	L		DB99.VAR10.VAR10_3[2].VAR10_3_2[1]
	__ASSERT==	__ACCU 1,	3
	L		DB99.VAR10.VAR10_3[2].VAR10_3_2[2]
	__ASSERT==	__ACCU 1,	4
	L		DB99.VAR10.VAR10_4
	__ASSERT==	__ACCU 1,	104
	L		DB99.VAR20[4].VAR20_1
	__ASSERT==	__ACCU 1,	W#16#204
	L		DB99.VAR20[5].VAR20_1
	__ASSERT==	__ACCU 1,	W#16#205
	L		DB99.VAR1
	__ASSERT==	__ACCU 1,	DW#16#111


	// Check DB 10 initial values
	AUF	DB 10
	L	DBLG
	__ASSERT==	__ACCU 1,	30
	L		DB10.DBVAR0
	__ASSERT==	__ACCU 1,	L#9100
	L		DB10.DBVAR1.DBVAR1_1
	__ASSERT==	__ACCU 1,	9101
	L		DB10.DBVAR1.DBVAR1_2
	__ASSERT==	__ACCU 1,	L#9102
	L		DB10.DBVAR1.DBVAR1_3.DBVAR1_3_1
	__ASSERT==	__ACCU 1,	9103
	L		DB10.DBVAR1.DBVAR1_3.DBVAR1_3_2
	__ASSERT==	__ACCU 1,	9104
	L		DB10.DBVAR2[1].DBVAR2_1
	__ASSERT==	__ACCU 1,	DW#16#9105
	L		DB10.DBVAR2[1].DBVAR2_2[1]
	__ASSERT==	__ACCU 1,	W#16#9106
	L		DB10.DBVAR2[1].DBVAR2_2[2]
	__ASSERT==	__ACCU 1,	W#16#9107
	L		DB10.DBVAR2[2].DBVAR2_1
	__ASSERT==	__ACCU 1,	DW#16#9108
	L		DB10.DBVAR2[2].DBVAR2_2[1]
	__ASSERT==	__ACCU 1,	W#16#9109
	L		DB10.DBVAR2[2].DBVAR2_2[2]
	__ASSERT==	__ACCU 1,	W#16#9110


	// Check DB 1 (FB 1 instance DB) initial values
	AUF	DB 1
	L	DBLG
	__ASSERT==	__ACCU 1,	30
	L		DB1.FBVAR0
	__ASSERT==	__ACCU 1,	L#100
	L		DB1.FBVAR1.FBVAR1_1
	__ASSERT==	__ACCU 1,	101
	L		DB1.FBVAR1.FBVAR1_2
	__ASSERT==	__ACCU 1,	L#102
	L		DB1.FBVAR1.FBVAR1_3.FBVAR1_3_1
	__ASSERT==	__ACCU 1,	103
	L		DB1.FBVAR1.FBVAR1_3.FBVAR1_3_2
	__ASSERT==	__ACCU 1,	104
	L		DB1.FBVAR2[1].FBVAR2_1
	__ASSERT==	__ACCU 1,	DW#16#105
	L		DB1.FBVAR2[1].FBVAR2_2[1]
	__ASSERT==	__ACCU 1,	W#16#106
	L		DB1.FBVAR2[1].FBVAR2_2[2]
	__ASSERT==	__ACCU 1,	W#16#107
	L		DB1.FBVAR2[2].FBVAR2_1
	__ASSERT==	__ACCU 1,	DW#16#108
	L		DB1.FBVAR2[2].FBVAR2_2[1]
	__ASSERT==	__ACCU 1,	W#16#109
	L		DB1.FBVAR2[2].FBVAR2_2[2]
	__ASSERT==	__ACCU 1,	W#16#110


	// Call FB with STRUCT and ARRAY parameters.
	CALL	FB 1, DB 1 (
		FBVAR0		:= DB10.DBVAR0,
		FBVAR1		:= DB10.DBVAR1,
		FBVAR2		:= DB10.DBVAR2,
	)


	// Call FC with STRUCT and ARRAY parameters.
	CALL	FC 1 (
		FCVAR0		:= DB10.DBVAR0,
		FCVAR1		:= DB10.DBVAR1,
		FCVAR2		:= DB10.DBVAR2,
	)


	CALL SFC 46 // STOP CPU
END_ORGANIZATION_BLOCK
