What function can I call from inside a C program, to discover what z/OS environment the program is being run in, e.g. is it z/OS UNIX (aka USS) or is it from TSO, say via JCL?
Identify environment, z/OS UNIX vs JCL or TSO
826 Views Asked by Morag Hughson At
1
There are 1 best solutions below
Related Questions in C
- How to call a C language function from x86 assembly code?
- What does: "char *argv[]" mean?
- User input sanitization program, which takes a specific amount of arguments and passes the execution to a bash script
- How to crop a BMP image in half using C
- How can I get the difference in minutes between two dates and hours?
- Why will this code compile although it defines two variables with the same name?
- Compiling eBPF program in Docker fails due to missing '__u64' type
- Why can't I use the file pointer after the first read attempt fails?
- #include Header files in C with definition too
- OpenCV2 on CLion
- What is causing the store latency in this program?
- How to refer to the filepath of test data in test sourcecode?
- 9 Digit Addresses in Hexadecimal System in MacOS
- My server TCP doesn't receive messages from the client in C
- Printing the characters obtained from the array s using printf?
Related Questions in MAINFRAME
- Where can I download ECI resource adapter (cicseci.rar). Unable to find out it in IBM portal
- Mainframe Programming Sorting, OUTFIL REMOVECC,NODETAIL
- Z/OS Cobol 6.3 copy: how to include only a chunk?
- SHA256 Checksum of a File transmitted from Mainframe to Azure
- open fetch and close cursor DB2
- How to "stack" an ISPF command?
- DB2 contention issues
- IBM z/OS TSO ISPF Editor Cancel command - how to add "Are You Sure?" query dialog
- FIlling a zone with S9(5)V9(8) COMP-3
- Mainframe monitoring using Zabbix
- How to programmatically overwrite DCI 2.0 policy via REXX or JCL?
- SEARCH ALL with a key PIC XX
- Why is this COBOL code failing to compile?
- Use MVS Dsname conventions. Mainframe name convention while downloading ftp using python
- COBOL issue (Compiling and executing)
Related Questions in ZOS
- Z/OS Cobol 6.3 copy: how to include only a chunk?
- Using the 'Download ZIP' option on Github Rep with z/OS?
- How to "stack" an ISPF command?
- How to use LISTDSI under OMVS
- Can I use an EQU in z/OS HL/ASM for a value in a DC?
- How do I package a object module replacement for distribution via smpe
- Trying to OPEN a PDSE and write records to a new member using z/OS HL/ASM
- How to programmatically overwrite DCI 2.0 policy via REXX or JCL?
- Connect to Db2 on z/OS from Windows. Connection failed due to a license error
- BPX2OPN fails when trying to open existing file for read/stat
- How do I write current date and time to a sequential dataset using JCL?
- How do I get the parameters passed in to an assembler program running in the UNIX System Services environment on z/OS?
- Compehending fields: ALLOC, FREE and %FR in FDReport product from BMC for mainframe
- zsh associative array has multiple keys with the same value
- U4091 Reason 00000006
Related Questions in USS
- is it possible to Run node js executables in USS/OMVS mainframe?
- How to use CP to copy variable length datasets and pds members?
- How do I find the documentation for shell builtins for z/OS?
- Using ANTLR on IBM USS
- Identify environment, z/OS UNIX vs JCL or TSO
- How to write a z/OS Health Check?
- USS memory mapping with malloc(s) in process
- Change directory in REXX exec running in z/OS USS?
- Siemens USS software stack
- Connect between PID and port on ZOS
- JAVA runtime exec throwing IOException for netstat command in mainframe USS environment
- PSS/USS Linux-Android. Does Pss contain Uss?
- Does PSS (Proportional Set Size) number for a process include the memory consumed by kernel code?
- Command not found although in PATH
- Why is z/OS USS "date" command output different from TSO TIME?
Trending Questions
- UIImageView Frame Doesn't Reflect Constraints
- Is it possible to use adb commands to click on a view by finding its ID?
- How to create a new web character symbol recognizable by html/javascript?
- Why isn't my CSS3 animation smooth in Google Chrome (but very smooth on other browsers)?
- Heap Gives Page Fault
- Connect ffmpeg to Visual Studio 2008
- Both Object- and ValueAnimator jumps when Duration is set above API LvL 24
- How to avoid default initialization of objects in std::vector?
- second argument of the command line arguments in a format other than char** argv or char* argv[]
- How to improve efficiency of algorithm which generates next lexicographic permutation?
- Navigating to the another actvity app getting crash in android
- How to read the particular message format in android and store in sqlite database?
- Resetting inventory status after order is cancelled
- Efficiently compute powers of X in SSE/AVX
- Insert into an external database using ajax and php : POST 500 (Internal Server Error)
Popular Questions
- How do I undo the most recent local commits in Git?
- How can I remove a specific item from an array in JavaScript?
- How do I delete a Git branch locally and remotely?
- Find all files containing a specific text (string) on Linux?
- How do I revert a Git repository to a previous commit?
- How do I create an HTML button that acts like a link?
- How do I check out a remote Git branch?
- How do I force "git pull" to overwrite local files?
- How do I list all files of a directory?
- How to check whether a string contains a substring in JavaScript?
- How do I redirect to another webpage?
- How can I iterate over rows in a Pandas DataFrame?
- How do I convert a String to an int in Java?
- Does Python have a string 'contains' substring method?
- How do I check if a string contains a specific word?
There are two approaches: CEE3INF, and rummage through the z/OS data areas.
CEE3INF has the advantage of being documented and portable to any LE environment, as well as providing information about PIPI that you don't easily find in the z/OS structures.
As an alternative to CEE3INF, there's plenty of information in the system data areas if you just need to distinguish between Batch, TSO, CICS and whether or not you've been dubbed as a USS process. The alternative is easy, and it's especially helpful outside the LE environment...though it's even easy to do in C by just loading up some pointers that you can get by using the XLC DSECT to C-structure conversion utility.
A TSO address space is one where ASCBTSB is non-zero (PSAAOLD->ASCBTSB). A Batch job is one where ASCBJBNI is filled in (PSAAOLD->ASCBJBNI). A CICS address space has TCBCAUF set non-zero (PSATOLD->TCBCAUF).
In any of the above, you can also check whether your task has been dubbed as a UNIX process by checking TCB->STCB->STCBOTCB. If non-zero, you've been dubbed and can use UNIX Services. The OTCBPRLI field has process information like the PID, and THLI has thread-level information.
Note that a given task might be eligible to use USS functions, but it hasn't yet. The "querydub()" function can help you distinguish between a task that's already been dubbed, versus one that can be, but just hasn't been yet.
If you use CEE3INF, there have been some comments about it not working properly outside of the main() function, but I think the issue is a small bug in the sample IBM provides in their documentation. This sample works fine on my z/OS 2.3 and 2.4 systems:
This is the sample code from the IBM manual, except notice in the call to CEE3INF, the IBM doc has a bug ("...fc" instead of "...&fc"). There were comments about CEE3INF not working if called outside of main(), but I think the issue is simply the bug in the sample above.
To test, I compile the code above under the UNIX Services shell using this command:
I then run the executable from a z/OS shell session:
This is a z/OS 2.3 system - I get identical results on 2.4.
UPDATE: What does "running in the z/OS UNIX Services environment" mean?
It's easy to understand batch jobs versus TSO sessions versus started tasks, but what's meant by "running in the z/OS UNIX Services environment"? In subsystems like CICS, IMS, or WebSphere "running under xxx" is easy to define because the transactions run inside a special type of service address space...but unfortunately, UNIX Services isn't like that.
Indeed, just about any task running on z/OS can make use of z/OS UNIX Services, so there really isn't a "z/OS UNIX Services environment" that you can define in a traditional way. A parallel would be VSAM...is a program that opens a VSAM file "running in VSAM?". We might care about programs running IDCAMS, programs opening VSAM files, programs using CICS/VSAM - but "running in VSAM" isn't particularly meaningful without further qualification. Plus, "running in VSAM" isn't exclusive with running as batch, STC or TSO user - it's the same with z/OS UNIX services - you can be a batch job, a started task or a TSO user, AND you can also be "running in z/OS UNIX Services" or not.
Here are three very different definitions of "running in z/OS UNIX Services":
Why would any of this matter? Well, some software - especially things like runtime library functions called by other applications - behaves differently depending on whether the caller is a UNIX process or not.
Imagine writing an "OPEN" function that gets passed a filename as an argument. If your caller is a UNIX process, you might interpret the filename as an actual filename...OPEN(XYZ) is interpreted as "check the current working directory for a file called 'XYZ'". But if the caller isn't dubbed as a UNIX process, then OPEN(XYZ) might mean to open the 'XYZ' DD statement. You can make this determination using the approach I outlined above, since it tells you that your task is in fact dubbed as a UNIX process.
Okay, but what's different between this and #2 above (running under the shell)?
Here's one example. Suppose you have a callable routine that wants to write a message to an output file. Most non-mainframe UNIX applications would simply write to STDOUT or STDERR, but this doesn't always work on z/OS because many applications are UNIX processes, but they aren't running under the shell - and without the shell, STDOUT and STDERR may not exist.
Here's the scenario...
You run a conventional program that has nothing to do with UNIX Services, but it does something to get itself dubbed as a UNIX process. Just as an example, maybe someone puts "DD PATH=/some/unix/file" in the JCL of an age-old COBOL program...miraculously, when this COBOL batch job runs, it's a UNIX process because it makes use of the UNIX Services filesystem. There are lots of things that can get your task dubbed as a UNIX process...DD PATH is one, but even calling a function that opens a TCP/IP socket or something similarly benign can do the trick. Maybe you're writing a vendor product that's just a batch assembler program, but it opens a TCP/IP socket...that's another common example of UNIX processes that run without a shell.
So why is this a problem? Well, think about what happens if that callable function decides to write it's messages to STDERR. Maybe it tests to see if it's running as a UNIX Services process, and if so it writes to STDERR, otherwise it dynamically allocates and writes to a SYSOUT file. Sounds simple, but it won't work for my example of an app having DD PATH.
Where does STDERR come from? Normally, the UNIX shell program sets it up - when you run a program under the shell, the shell typically passes your program three pre-opened file handles for STDIN, STDOUT and STDERR. Since there's no shell in my sample scenario, these file handles weren't passed to the application, so a write to STDERR is going to fail. In fact, there are many things that the shell passes to a child process besides STDIN/STDOUT/STDERR, such as environment variables, signal handling and so forth. (Certainly, the user can manually allocate STDIN/STDOUT/STDERR in his JCL...I'm not talking about that here).
If you want to have software that can handle both running under the shell and not running under the shell, you have more work to do than just seeing if your application has been dubbed as a UNIX process:
As for my third example - LE programs running with POSIX(ON) - this is largely an issue for developers writing in high-level languages based on the LE runtime, since the behaviors of certain runtime functions are different with POSIX(ON) or POSIX(OFF).
An example is the C programmer writing a function that can be called by both POSIX(ON) and POSIX(OFF) callers. Let's say the function wants to do some background processing under a separate thread...in POSIX(ON) applications, the developer might use pthread_create(), but this won't work in POSIX(OFF). There are actually lots of things in IBM's LE runtime that behave differently depending on the POSIX setting: threads, signal handling, etc etc etc. If you hope to write "universal" code and you need these functions, you'll definitely need to query the POSIX setting at execution time and take different paths depending on how it's set.
So hopefully that sheds some light on the complexity hiding behind this question...three different definitions of "running in z/OS UNIX environment", and three different use-cases illustrating why each is important.