diff options
| author | Eric Windisch <eric@cloudscaling.com> | 2013-02-12 01:13:17 -0500 |
|---|---|---|
| committer | Eric Windisch <eric@cloudscaling.com> | 2013-03-12 15:28:14 -0400 |
| commit | 40640215468b1fe7f7b17c299c658e94f82e7d70 (patch) | |
| tree | e9d914b6c2400ec065b58ef42b451a752854b268 | |
| parent | 21925b63af87c36be97eec5b212e06477471bb1e (diff) | |
Sanitize input before creating IPC socket.
Sockets are created by the zeromq driver
for the topic specified by each incoming message.
Because the topic is arbitrarily supplied by the sender,
path separators in the topic must be illegal.
Fixes bug 1122763
Change-Id: Iccdb9b69e646bfe7665ee34c367fd4019db25f17
| -rw-r--r-- | openstack/common/rpc/impl_zmq.py | 10 | ||||
| -rw-r--r-- | tests/unit/rpc/test_zmq.py | 19 |
2 files changed, 29 insertions, 0 deletions
diff --git a/openstack/common/rpc/impl_zmq.py b/openstack/common/rpc/impl_zmq.py index 7af9cd0..87f8d21 100644 --- a/openstack/common/rpc/impl_zmq.py +++ b/openstack/common/rpc/impl_zmq.py @@ -16,6 +16,7 @@ import os import pprint +import re import socket import sys import types @@ -431,6 +432,8 @@ class ZmqProxy(ZmqBaseReactor): def __init__(self, conf): super(ZmqProxy, self).__init__(conf) + pathsep = set((os.path.sep or '', os.path.altsep or '', '/', '\\')) + self.badchars = re.compile(r'[%s]' % re.escape(''.join(pathsep))) self.topic_proxy = {} @@ -456,6 +459,13 @@ class ZmqProxy(ZmqBaseReactor): LOG.info(_("Creating proxy for topic: %s"), topic) try: + # The topic is received over the network, + # don't trust this input. + if self.badchars.search(topic) is not None: + emsg = _("Topic contained dangerous characters.") + LOG.warn(emsg) + raise RPCException(emsg) + out_sock = ZmqSocket("ipc://%s/zmq_topic_%s" % (ipc_dir, topic), sock_type, bind=True) diff --git a/tests/unit/rpc/test_zmq.py b/tests/unit/rpc/test_zmq.py index c197c35..d42a07d 100644 --- a/tests/unit/rpc/test_zmq.py +++ b/tests/unit/rpc/test_zmq.py @@ -21,6 +21,7 @@ Unit Tests for remote procedure calls using zeromq import eventlet eventlet.monkey_patch() +import itertools import logging import os import socket @@ -100,6 +101,24 @@ class _RpcZmqBaseTestCase(common.BaseRpcTestCase): if self.reactor: self.reactor.close() + def test_cast_pathsep_topic(self): + """Ensure topics with a contain a path separator result in error.""" + tmp_topic = self.topic_nested + + # All OS path separators + badchars = itertools.ifilter(None, + set((os.sep, os.altsep, '/', '\\'))) + for char in badchars: + self.topic_nested = char.join(('hello', 'world')) + try: + # TODO(ewindisch): Determine which exception is raised. + # pending bug #1121348 + self.assertRaises(Exception, self._test_cast, + common.TestReceiver.echo, 42, {"value": 42}, + fanout=False) + finally: + self.topic_nested = tmp_topic + class RpcZmqBaseTopicTestCase(_RpcZmqBaseTestCase): """ |
