Ask Your Question
0

multiprocessing: rospy.init_node() has already been called

asked 2020-09-14 12:29:11 -0500

azerila gravatar image

updated 2020-09-14 12:32:21 -0500

I have a python script which initializes a node through rospy.init_node() and in a later line it does the following:

robot2 = multiprocessing.Process(target=robot, kwargs={'robot_ip': ip2, 'uri': uri})
robot2.start()

which involves starting a new roscore with a new uri, changing the environmental variable by os.environ["ROS_MASTER_URI"] = "http://localhost:" + uri and initializing a new node with rospy.init_node(). However, for the second node the it gives the error that rospy.init_node() is already called.

My expectation however is that since the second node is made after in a seperate process, with separate roscore, and separate environmental variable, this error should not come.

An example similar to my code is the following:

class TheRobot(object):
    def __init__(self,
                 robot_ip='172.16.1.2',
                 **kwargs):

        self.uri  = str(uri)
        os.environ["ROS_MASTER_URI"] = "http://localhost:" + self.uri
        venv = os.environ.copy()
        self.roscore_proc = subprocess.Popen(["roscore", '-p', self.uri],
                                             stdout=None,  
                                             stderr=sys.stderr,
                                             preexec_fn=os.setsid
                                             )
        rospy.init_node('robot_setup_node_{}'.format(self.uri))




class DoubleRobot(TheRobot):
    def __init__(self, 
                 ip1='172.16.0.2',
                 ip2='172.16.1.2',
                 uri=None,
                 **kwargs):

        super().__init__(robot_ip=ip1, uri=uri)
        robot2 = multiprocessing.Process(target=TheRobot, kwargs={'robot_ip': ip2, 'uri': uri+1})
        robot2.start()


twin_panda = DoubleRobot(ip1='172.16.0.2', ip2='172.16.1.2', uri=11314)

a similar question but without multiprocessing can be found here but it did not help. In general,I'd be grateful for any suggestion for the above purpose, or for any other alternative.

edit retag flag offensive close merge delete

Comments

The suggestion would be: do not use multiprocessing with rospy.

It's not compatible. There are multiple Q&As here on this site about this topic.

gvdhoorn gravatar image gvdhoorn  ( 2020-09-15 05:32:45 -0500 )edit

@gvdhoorn the better alternative is maybe python subprocess right? It's strange though if the two are having separate roscores but can't have separate rospy node

azerila gravatar image azerila  ( 2020-09-15 06:23:00 -0500 )edit
1

It's strange though if the two are having separate roscores but can't have separate rospy node

Popen is something entirely different from how multiprocessing works.

The first uses regular system calls to start a new process (ie: the OS starts a new process). The second uses fork(..)ing.

That's a different approach, and cannot be simply considered to be "multiple processes".

gvdhoorn gravatar image gvdhoorn  ( 2020-09-15 06:26:50 -0500 )edit

@gvdhoorn interesting, thanks for the note! Although I'm not sure what to use without interrupting the main process that runs the first robot. It might be safest to just use another computer to have the second robot running. Or do you think subprocess could still be applicable for the second robot in the same computer?

azerila gravatar image azerila  ( 2020-09-15 06:36:12 -0500 )edit

I have no idea what your requirements are, nor what you are doing exactly now, so I cannot really make any recommendations.

gvdhoorn gravatar image gvdhoorn  ( 2020-09-15 07:17:21 -0500 )edit

So basically I have two Franka Emika robots that I want them to work together and both are controlled through ros_control. The only technical issue that I could think likely was if the network card on my computer may cause too many packet loss but I have already tested this. On my main thread I want to decide which robot to control by changing the uri environmental variable and publish the control command (roughly speaking). In general though one of the robots for most of the time will remain still and I just want the other one to work with no interruption or issue.This should work for sure if I have both robots connected to separate computers but for convenience I want to give it a try and see if it will work on a single computer.

azerila gravatar image azerila  ( 2020-09-15 10:09:04 -0500 )edit

1 Answer

Sort by ยป oldest newest most voted
0

answered 2020-09-15 11:09:10 -0500

azerila gravatar image

updated 2020-09-15 11:09:51 -0500

Solved it with the following:

    context = 'spawn'
    ctx = mp.get_context(context)
    robot2 = ctx.Process(target=robot1, kwargs={'robot_ip': ip2, 'uri': uri+1})
    robot2.daemon = True
    robot2.start()

However, in the same script on top I have to also add:

paths = [...some paths, ...]
for path in reversed(paths):  
    sys.path.insert(0, os.path.expanduser(path))

which I'm not sure if there's a better solution for it. but it works.

edit flag offensive delete link more

Your Answer

Please start posting anonymously - your entry will be published after you log in or create a new account.

Add Answer

Question Tools

1 follower

Stats

Asked: 2020-09-14 12:29:11 -0500

Seen: 29 times

Last updated: Sep 15