Get child process operation result from parent process












0















I know I can read parent's information in a child process by exporting a variable



myVariable=1
bash
echo $myVariable

exit
export myVariable=1
bash
echo $myVariable # 1


How can I access the variables defined in the child process from the parent?



bash
a=2
suspend
echo $a










share|improve this question



























    0















    I know I can read parent's information in a child process by exporting a variable



    myVariable=1
    bash
    echo $myVariable

    exit
    export myVariable=1
    bash
    echo $myVariable # 1


    How can I access the variables defined in the child process from the parent?



    bash
    a=2
    suspend
    echo $a










    share|improve this question

























      0












      0








      0








      I know I can read parent's information in a child process by exporting a variable



      myVariable=1
      bash
      echo $myVariable

      exit
      export myVariable=1
      bash
      echo $myVariable # 1


      How can I access the variables defined in the child process from the parent?



      bash
      a=2
      suspend
      echo $a










      share|improve this question














      I know I can read parent's information in a child process by exporting a variable



      myVariable=1
      bash
      echo $myVariable

      exit
      export myVariable=1
      bash
      echo $myVariable # 1


      How can I access the variables defined in the child process from the parent?



      bash
      a=2
      suspend
      echo $a







      bash process






      share|improve this question













      share|improve this question











      share|improve this question




      share|improve this question










      asked Feb 1 at 0:53









      jedijedi

      281113




      281113






















          2 Answers
          2






          active

          oldest

          votes


















          1














          You can't do this.



          When you start a new shell, it's an unrelated process and the parent can't "look inside" it to see what it has in memory (this is a security boundary of sorts). Its variables are not shared and not published where someone else can see them.



          It gets a copy of the existing environment variables, but any changes it makes to them are for itself alone, and its children. There's no "backwards" communication until the shell exits, and all there is at that point is a single exit code.



          When you're doing this interactively as you've shown, that's the end of the story. Your best bet is to save data into a file, which you can then read from or source back in to the parent. If you really can't use a file, I have an awful way of doing it right at the end, but I recommend rethinking what you're trying to achieve - it'd be nice to be able to make this work normally (and some other shells do have shared variables!), it's just not achievable here.



          If you're making a program or shell script that runs non-interactively, some or all of source, eval, and printing out data to standard output may help you, as noted in an existing answer. If you exit the child shell, you can pass a single byte of information back in your exit code with exit 123, which you can read with $? in the parent.





          If you really really need to migrate something out, here is a very nasty hack to achieve it interactively with no intermediate files:



          $ bash
          $ export a=2
          $ sleep 60 & echo $!
          2198
          $ suspend
          $ xargs -0 < /proc/2198/environ printf '%sn' | grep '^a='
          a=2
          $ a=$(xargs -0 < /proc/2198/environ printf '%sn' | grep '^a=' | cut -d= -f2-)
          $ echo $a
          2
          $ [1]+ Done sleep 60


          There are significant limitations here, particularly if you're not in control of the whole environment - a newline within an environment variable value could trick you into setting a value you didn't want, for example.



          This works by exporting a so that it appears in the environment of subprocesses and then launching one (sleep 60 here), in the background (&), with the PID of sleep printed out (echo $!). When you suspend the inner shell, you can read the sleep process's environment variables given by its parent from the outside - those are public in the /proc filesystem - but they're separated by null bytes, so xargs -0 splits them up and printf '%sn' outputs one per line. At that point there's a complete list of variables, and we can grep out the one we want, optionally chopping out just the value after the = with cut and setting it. The sleep will end on its own, which is what we see at the end of the transcript ([1]+ Done ...).



          You'd need to do it all again if you wanted to pick up on a change to a in the child - and the child will never see a change that you make to a in the parent: all we've done is make another copy. The reason for the sleep process is that we can only see the inbound environment variables of a process, and not any of the shell's internal variable values even if they're exported.



          I don't recommend doing this or relying on it, and I can't see any value in using it, but if you do end up in a situation where it's truly, vitally necessary then it should work.






          share|improve this answer
























          • This is a terrific answer! I asked myself this question while making an exrcise so no real world scenario to achieve what I was asking for. I wanted to know this just for an exercise and for my personal interest. If I had to, I would definitely use your recommended way, no nasty hacks ;) But thanks for the hack anyway ;) Thank you for rationale and a substantive and educational response. I give you +1. Thank you!

            – jedi
            Feb 1 at 9:48



















          1














          From this question on Stack Overflow the solution is to use source when executing the child process:



          In a.sh do source b.sh instead of ./b.sh





          a.sh should look like this :



          #!/bin/bash
          export A=1
          source b.sh
          echo parent "$A"





          share|improve this answer
























          • Is it possible to achieve what I want without having to create files? Just in the terminal.

            – jedi
            Feb 1 at 1:58











          • See unix.stackexchange.com/questions/420990/…

            – Kristopher Ives
            Feb 1 at 2:09











          Your Answer








          StackExchange.ready(function() {
          var channelOptions = {
          tags: "".split(" "),
          id: "89"
          };
          initTagRenderer("".split(" "), "".split(" "), channelOptions);

          StackExchange.using("externalEditor", function() {
          // Have to fire editor after snippets, if snippets enabled
          if (StackExchange.settings.snippets.snippetsEnabled) {
          StackExchange.using("snippets", function() {
          createEditor();
          });
          }
          else {
          createEditor();
          }
          });

          function createEditor() {
          StackExchange.prepareEditor({
          heartbeatType: 'answer',
          autoActivateHeartbeat: false,
          convertImagesToLinks: true,
          noModals: true,
          showLowRepImageUploadWarning: true,
          reputationToPostImages: 10,
          bindNavPrevention: true,
          postfix: "",
          imageUploader: {
          brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
          contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
          allowUrls: true
          },
          onDemand: true,
          discardSelector: ".discard-answer"
          ,immediatelyShowMarkdownHelp:true
          });


          }
          });














          draft saved

          draft discarded


















          StackExchange.ready(
          function () {
          StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2faskubuntu.com%2fquestions%2f1114589%2fget-child-process-operation-result-from-parent-process%23new-answer', 'question_page');
          }
          );

          Post as a guest















          Required, but never shown

























          2 Answers
          2






          active

          oldest

          votes








          2 Answers
          2






          active

          oldest

          votes









          active

          oldest

          votes






          active

          oldest

          votes









          1














          You can't do this.



          When you start a new shell, it's an unrelated process and the parent can't "look inside" it to see what it has in memory (this is a security boundary of sorts). Its variables are not shared and not published where someone else can see them.



          It gets a copy of the existing environment variables, but any changes it makes to them are for itself alone, and its children. There's no "backwards" communication until the shell exits, and all there is at that point is a single exit code.



          When you're doing this interactively as you've shown, that's the end of the story. Your best bet is to save data into a file, which you can then read from or source back in to the parent. If you really can't use a file, I have an awful way of doing it right at the end, but I recommend rethinking what you're trying to achieve - it'd be nice to be able to make this work normally (and some other shells do have shared variables!), it's just not achievable here.



          If you're making a program or shell script that runs non-interactively, some or all of source, eval, and printing out data to standard output may help you, as noted in an existing answer. If you exit the child shell, you can pass a single byte of information back in your exit code with exit 123, which you can read with $? in the parent.





          If you really really need to migrate something out, here is a very nasty hack to achieve it interactively with no intermediate files:



          $ bash
          $ export a=2
          $ sleep 60 & echo $!
          2198
          $ suspend
          $ xargs -0 < /proc/2198/environ printf '%sn' | grep '^a='
          a=2
          $ a=$(xargs -0 < /proc/2198/environ printf '%sn' | grep '^a=' | cut -d= -f2-)
          $ echo $a
          2
          $ [1]+ Done sleep 60


          There are significant limitations here, particularly if you're not in control of the whole environment - a newline within an environment variable value could trick you into setting a value you didn't want, for example.



          This works by exporting a so that it appears in the environment of subprocesses and then launching one (sleep 60 here), in the background (&), with the PID of sleep printed out (echo $!). When you suspend the inner shell, you can read the sleep process's environment variables given by its parent from the outside - those are public in the /proc filesystem - but they're separated by null bytes, so xargs -0 splits them up and printf '%sn' outputs one per line. At that point there's a complete list of variables, and we can grep out the one we want, optionally chopping out just the value after the = with cut and setting it. The sleep will end on its own, which is what we see at the end of the transcript ([1]+ Done ...).



          You'd need to do it all again if you wanted to pick up on a change to a in the child - and the child will never see a change that you make to a in the parent: all we've done is make another copy. The reason for the sleep process is that we can only see the inbound environment variables of a process, and not any of the shell's internal variable values even if they're exported.



          I don't recommend doing this or relying on it, and I can't see any value in using it, but if you do end up in a situation where it's truly, vitally necessary then it should work.






          share|improve this answer
























          • This is a terrific answer! I asked myself this question while making an exrcise so no real world scenario to achieve what I was asking for. I wanted to know this just for an exercise and for my personal interest. If I had to, I would definitely use your recommended way, no nasty hacks ;) But thanks for the hack anyway ;) Thank you for rationale and a substantive and educational response. I give you +1. Thank you!

            – jedi
            Feb 1 at 9:48
















          1














          You can't do this.



          When you start a new shell, it's an unrelated process and the parent can't "look inside" it to see what it has in memory (this is a security boundary of sorts). Its variables are not shared and not published where someone else can see them.



          It gets a copy of the existing environment variables, but any changes it makes to them are for itself alone, and its children. There's no "backwards" communication until the shell exits, and all there is at that point is a single exit code.



          When you're doing this interactively as you've shown, that's the end of the story. Your best bet is to save data into a file, which you can then read from or source back in to the parent. If you really can't use a file, I have an awful way of doing it right at the end, but I recommend rethinking what you're trying to achieve - it'd be nice to be able to make this work normally (and some other shells do have shared variables!), it's just not achievable here.



          If you're making a program or shell script that runs non-interactively, some or all of source, eval, and printing out data to standard output may help you, as noted in an existing answer. If you exit the child shell, you can pass a single byte of information back in your exit code with exit 123, which you can read with $? in the parent.





          If you really really need to migrate something out, here is a very nasty hack to achieve it interactively with no intermediate files:



          $ bash
          $ export a=2
          $ sleep 60 & echo $!
          2198
          $ suspend
          $ xargs -0 < /proc/2198/environ printf '%sn' | grep '^a='
          a=2
          $ a=$(xargs -0 < /proc/2198/environ printf '%sn' | grep '^a=' | cut -d= -f2-)
          $ echo $a
          2
          $ [1]+ Done sleep 60


          There are significant limitations here, particularly if you're not in control of the whole environment - a newline within an environment variable value could trick you into setting a value you didn't want, for example.



          This works by exporting a so that it appears in the environment of subprocesses and then launching one (sleep 60 here), in the background (&), with the PID of sleep printed out (echo $!). When you suspend the inner shell, you can read the sleep process's environment variables given by its parent from the outside - those are public in the /proc filesystem - but they're separated by null bytes, so xargs -0 splits them up and printf '%sn' outputs one per line. At that point there's a complete list of variables, and we can grep out the one we want, optionally chopping out just the value after the = with cut and setting it. The sleep will end on its own, which is what we see at the end of the transcript ([1]+ Done ...).



          You'd need to do it all again if you wanted to pick up on a change to a in the child - and the child will never see a change that you make to a in the parent: all we've done is make another copy. The reason for the sleep process is that we can only see the inbound environment variables of a process, and not any of the shell's internal variable values even if they're exported.



          I don't recommend doing this or relying on it, and I can't see any value in using it, but if you do end up in a situation where it's truly, vitally necessary then it should work.






          share|improve this answer
























          • This is a terrific answer! I asked myself this question while making an exrcise so no real world scenario to achieve what I was asking for. I wanted to know this just for an exercise and for my personal interest. If I had to, I would definitely use your recommended way, no nasty hacks ;) But thanks for the hack anyway ;) Thank you for rationale and a substantive and educational response. I give you +1. Thank you!

            – jedi
            Feb 1 at 9:48














          1












          1








          1







          You can't do this.



          When you start a new shell, it's an unrelated process and the parent can't "look inside" it to see what it has in memory (this is a security boundary of sorts). Its variables are not shared and not published where someone else can see them.



          It gets a copy of the existing environment variables, but any changes it makes to them are for itself alone, and its children. There's no "backwards" communication until the shell exits, and all there is at that point is a single exit code.



          When you're doing this interactively as you've shown, that's the end of the story. Your best bet is to save data into a file, which you can then read from or source back in to the parent. If you really can't use a file, I have an awful way of doing it right at the end, but I recommend rethinking what you're trying to achieve - it'd be nice to be able to make this work normally (and some other shells do have shared variables!), it's just not achievable here.



          If you're making a program or shell script that runs non-interactively, some or all of source, eval, and printing out data to standard output may help you, as noted in an existing answer. If you exit the child shell, you can pass a single byte of information back in your exit code with exit 123, which you can read with $? in the parent.





          If you really really need to migrate something out, here is a very nasty hack to achieve it interactively with no intermediate files:



          $ bash
          $ export a=2
          $ sleep 60 & echo $!
          2198
          $ suspend
          $ xargs -0 < /proc/2198/environ printf '%sn' | grep '^a='
          a=2
          $ a=$(xargs -0 < /proc/2198/environ printf '%sn' | grep '^a=' | cut -d= -f2-)
          $ echo $a
          2
          $ [1]+ Done sleep 60


          There are significant limitations here, particularly if you're not in control of the whole environment - a newline within an environment variable value could trick you into setting a value you didn't want, for example.



          This works by exporting a so that it appears in the environment of subprocesses and then launching one (sleep 60 here), in the background (&), with the PID of sleep printed out (echo $!). When you suspend the inner shell, you can read the sleep process's environment variables given by its parent from the outside - those are public in the /proc filesystem - but they're separated by null bytes, so xargs -0 splits them up and printf '%sn' outputs one per line. At that point there's a complete list of variables, and we can grep out the one we want, optionally chopping out just the value after the = with cut and setting it. The sleep will end on its own, which is what we see at the end of the transcript ([1]+ Done ...).



          You'd need to do it all again if you wanted to pick up on a change to a in the child - and the child will never see a change that you make to a in the parent: all we've done is make another copy. The reason for the sleep process is that we can only see the inbound environment variables of a process, and not any of the shell's internal variable values even if they're exported.



          I don't recommend doing this or relying on it, and I can't see any value in using it, but if you do end up in a situation where it's truly, vitally necessary then it should work.






          share|improve this answer













          You can't do this.



          When you start a new shell, it's an unrelated process and the parent can't "look inside" it to see what it has in memory (this is a security boundary of sorts). Its variables are not shared and not published where someone else can see them.



          It gets a copy of the existing environment variables, but any changes it makes to them are for itself alone, and its children. There's no "backwards" communication until the shell exits, and all there is at that point is a single exit code.



          When you're doing this interactively as you've shown, that's the end of the story. Your best bet is to save data into a file, which you can then read from or source back in to the parent. If you really can't use a file, I have an awful way of doing it right at the end, but I recommend rethinking what you're trying to achieve - it'd be nice to be able to make this work normally (and some other shells do have shared variables!), it's just not achievable here.



          If you're making a program or shell script that runs non-interactively, some or all of source, eval, and printing out data to standard output may help you, as noted in an existing answer. If you exit the child shell, you can pass a single byte of information back in your exit code with exit 123, which you can read with $? in the parent.





          If you really really need to migrate something out, here is a very nasty hack to achieve it interactively with no intermediate files:



          $ bash
          $ export a=2
          $ sleep 60 & echo $!
          2198
          $ suspend
          $ xargs -0 < /proc/2198/environ printf '%sn' | grep '^a='
          a=2
          $ a=$(xargs -0 < /proc/2198/environ printf '%sn' | grep '^a=' | cut -d= -f2-)
          $ echo $a
          2
          $ [1]+ Done sleep 60


          There are significant limitations here, particularly if you're not in control of the whole environment - a newline within an environment variable value could trick you into setting a value you didn't want, for example.



          This works by exporting a so that it appears in the environment of subprocesses and then launching one (sleep 60 here), in the background (&), with the PID of sleep printed out (echo $!). When you suspend the inner shell, you can read the sleep process's environment variables given by its parent from the outside - those are public in the /proc filesystem - but they're separated by null bytes, so xargs -0 splits them up and printf '%sn' outputs one per line. At that point there's a complete list of variables, and we can grep out the one we want, optionally chopping out just the value after the = with cut and setting it. The sleep will end on its own, which is what we see at the end of the transcript ([1]+ Done ...).



          You'd need to do it all again if you wanted to pick up on a change to a in the child - and the child will never see a change that you make to a in the parent: all we've done is make another copy. The reason for the sleep process is that we can only see the inbound environment variables of a process, and not any of the shell's internal variable values even if they're exported.



          I don't recommend doing this or relying on it, and I can't see any value in using it, but if you do end up in a situation where it's truly, vitally necessary then it should work.







          share|improve this answer












          share|improve this answer



          share|improve this answer










          answered Feb 1 at 5:21









          Michael HomerMichael Homer

          1575




          1575













          • This is a terrific answer! I asked myself this question while making an exrcise so no real world scenario to achieve what I was asking for. I wanted to know this just for an exercise and for my personal interest. If I had to, I would definitely use your recommended way, no nasty hacks ;) But thanks for the hack anyway ;) Thank you for rationale and a substantive and educational response. I give you +1. Thank you!

            – jedi
            Feb 1 at 9:48



















          • This is a terrific answer! I asked myself this question while making an exrcise so no real world scenario to achieve what I was asking for. I wanted to know this just for an exercise and for my personal interest. If I had to, I would definitely use your recommended way, no nasty hacks ;) But thanks for the hack anyway ;) Thank you for rationale and a substantive and educational response. I give you +1. Thank you!

            – jedi
            Feb 1 at 9:48

















          This is a terrific answer! I asked myself this question while making an exrcise so no real world scenario to achieve what I was asking for. I wanted to know this just for an exercise and for my personal interest. If I had to, I would definitely use your recommended way, no nasty hacks ;) But thanks for the hack anyway ;) Thank you for rationale and a substantive and educational response. I give you +1. Thank you!

          – jedi
          Feb 1 at 9:48





          This is a terrific answer! I asked myself this question while making an exrcise so no real world scenario to achieve what I was asking for. I wanted to know this just for an exercise and for my personal interest. If I had to, I would definitely use your recommended way, no nasty hacks ;) But thanks for the hack anyway ;) Thank you for rationale and a substantive and educational response. I give you +1. Thank you!

          – jedi
          Feb 1 at 9:48













          1














          From this question on Stack Overflow the solution is to use source when executing the child process:



          In a.sh do source b.sh instead of ./b.sh





          a.sh should look like this :



          #!/bin/bash
          export A=1
          source b.sh
          echo parent "$A"





          share|improve this answer
























          • Is it possible to achieve what I want without having to create files? Just in the terminal.

            – jedi
            Feb 1 at 1:58











          • See unix.stackexchange.com/questions/420990/…

            – Kristopher Ives
            Feb 1 at 2:09
















          1














          From this question on Stack Overflow the solution is to use source when executing the child process:



          In a.sh do source b.sh instead of ./b.sh





          a.sh should look like this :



          #!/bin/bash
          export A=1
          source b.sh
          echo parent "$A"





          share|improve this answer
























          • Is it possible to achieve what I want without having to create files? Just in the terminal.

            – jedi
            Feb 1 at 1:58











          • See unix.stackexchange.com/questions/420990/…

            – Kristopher Ives
            Feb 1 at 2:09














          1












          1








          1







          From this question on Stack Overflow the solution is to use source when executing the child process:



          In a.sh do source b.sh instead of ./b.sh





          a.sh should look like this :



          #!/bin/bash
          export A=1
          source b.sh
          echo parent "$A"





          share|improve this answer













          From this question on Stack Overflow the solution is to use source when executing the child process:



          In a.sh do source b.sh instead of ./b.sh





          a.sh should look like this :



          #!/bin/bash
          export A=1
          source b.sh
          echo parent "$A"






          share|improve this answer












          share|improve this answer



          share|improve this answer










          answered Feb 1 at 1:52









          Kristopher IvesKristopher Ives

          2,94211525




          2,94211525













          • Is it possible to achieve what I want without having to create files? Just in the terminal.

            – jedi
            Feb 1 at 1:58











          • See unix.stackexchange.com/questions/420990/…

            – Kristopher Ives
            Feb 1 at 2:09



















          • Is it possible to achieve what I want without having to create files? Just in the terminal.

            – jedi
            Feb 1 at 1:58











          • See unix.stackexchange.com/questions/420990/…

            – Kristopher Ives
            Feb 1 at 2:09

















          Is it possible to achieve what I want without having to create files? Just in the terminal.

          – jedi
          Feb 1 at 1:58





          Is it possible to achieve what I want without having to create files? Just in the terminal.

          – jedi
          Feb 1 at 1:58













          See unix.stackexchange.com/questions/420990/…

          – Kristopher Ives
          Feb 1 at 2:09





          See unix.stackexchange.com/questions/420990/…

          – Kristopher Ives
          Feb 1 at 2:09


















          draft saved

          draft discarded




















































          Thanks for contributing an answer to Ask Ubuntu!


          • Please be sure to answer the question. Provide details and share your research!

          But avoid



          • Asking for help, clarification, or responding to other answers.

          • Making statements based on opinion; back them up with references or personal experience.


          To learn more, see our tips on writing great answers.




          draft saved


          draft discarded














          StackExchange.ready(
          function () {
          StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2faskubuntu.com%2fquestions%2f1114589%2fget-child-process-operation-result-from-parent-process%23new-answer', 'question_page');
          }
          );

          Post as a guest















          Required, but never shown





















































          Required, but never shown














          Required, but never shown












          Required, but never shown







          Required, but never shown

































          Required, but never shown














          Required, but never shown












          Required, but never shown







          Required, but never shown







          Popular posts from this blog

          Biblatex bibliography style without URLs when DOI exists (in Overleaf with Zotero bibliography)

          ComboBox Display Member on multiple fields

          Is it possible to collect Nectar points via Trainline?