From 061cfb5258f27c895a070502d4f83a8c1a394561 Mon Sep 17 00:00:00 2001 From: Antoine Pitrou Date: Mon, 28 Feb 2011 22:25:22 +0000 Subject: [PATCH] Issue #10866: Add socket.sethostname(). Initial patch by Ross Lagerwall. --- Doc/library/socket.rst | 10 ++++++++++ Lib/test/test_socket.py | 20 ++++++++++++++++++++ Misc/NEWS | 2 ++ Modules/socketmodule.c | 35 +++++++++++++++++++++++++++++++++++ configure | 4 ++-- configure.in | 2 +- pyconfig.h.in | 21 ++++++++++++--------- 7 files changed, 82 insertions(+), 12 deletions(-) diff --git a/Doc/library/socket.rst b/Doc/library/socket.rst index 78b66e0c9d0..c456367e805 100644 --- a/Doc/library/socket.rst +++ b/Doc/library/socket.rst @@ -521,6 +521,16 @@ The module :mod:`socket` exports the following constants and functions: meanings. +.. function:: sethostname(name) + + Set the machine's hostname to *name*. This will raise a + :exc:`socket.error` if you don't have enough rights. + + Availability: Unix. + + .. versionadded:: 3.3 + + .. data:: SocketType This is a Python type object that represents the socket object type. It is the diff --git a/Lib/test/test_socket.py b/Lib/test/test_socket.py index 5a5a214b9e3..d761a73f2ff 100644 --- a/Lib/test/test_socket.py +++ b/Lib/test/test_socket.py @@ -325,6 +325,26 @@ class GeneralModuleTests(unittest.TestCase): if not fqhn in all_host_names: self.fail("Error testing host resolution mechanisms. (fqdn: %s, all: %s)" % (fqhn, repr(all_host_names))) + @unittest.skipUnless(hasattr(socket, 'sethostname'), "test needs socket.sethostname()") + @unittest.skipUnless(hasattr(socket, 'gethostname'), "test needs socket.gethostname()") + def test_sethostname(self): + oldhn = socket.gethostname() + try: + socket.sethostname('new') + except socket.error as e: + if e.errno == errno.EPERM: + self.skipTest("test should be run as root") + else: + raise + try: + # running test as root! + self.assertEqual(socket.gethostname(), 'new') + # Should work with bytes objects too + socket.sethostname(b'bar') + self.assertEqual(socket.gethostname(), 'bar') + finally: + socket.sethostname(oldhn) + def testRefCountGetNameInfo(self): # Testing reference count for getnameinfo if hasattr(sys, "getrefcount"): diff --git a/Misc/NEWS b/Misc/NEWS index 19400c8fbac..47f0de6b917 100644 --- a/Misc/NEWS +++ b/Misc/NEWS @@ -35,6 +35,8 @@ Core and Builtins Library ------- +- Issue #10866: Add socket.sethostname(). Initial patch by Ross Lagerwall. + - Issue #11140: Lock.release() now raises a RuntimeError when attempting to release an unacquired lock, as claimed in the threading documentation. The _thread.error exception is now an alias of RuntimeError. Patch by diff --git a/Modules/socketmodule.c b/Modules/socketmodule.c index 563395acdb4..687d9648868 100644 --- a/Modules/socketmodule.c +++ b/Modules/socketmodule.c @@ -3135,6 +3135,37 @@ PyDoc_STRVAR(gethostname_doc, \n\ Return the current host name."); +#ifdef HAVE_SETHOSTNAME +PyDoc_STRVAR(sethostname_doc, +"sethostname(name)\n\n\ +Sets the hostname to name."); + +static PyObject * +socket_sethostname(PyObject *self, PyObject *args) +{ + PyObject *hnobj; + Py_buffer buf; + int res, flag = 0; + + if (!PyArg_ParseTuple(args, "S:sethostname", &hnobj)) { + PyErr_Clear(); + if (!PyArg_ParseTuple(args, "O&:sethostname", + PyUnicode_FSConverter, &hnobj)) + return NULL; + flag = 1; + } + res = PyObject_GetBuffer(hnobj, &buf, PyBUF_SIMPLE); + if (!res) { + res = sethostname(buf.buf, buf.len); + PyBuffer_Release(&buf); + } + if (flag) + Py_DECREF(hnobj); + if (res) + return set_error(); + Py_RETURN_NONE; +} +#endif /* Python interface to gethostbyname(name). */ @@ -4233,6 +4264,10 @@ static PyMethodDef socket_methods[] = { METH_VARARGS, gethostbyaddr_doc}, {"gethostname", socket_gethostname, METH_NOARGS, gethostname_doc}, +#ifdef HAVE_SETHOSTNAME + {"sethostname", socket_sethostname, + METH_VARARGS, sethostname_doc}, +#endif {"getservbyname", socket_getservbyname, METH_VARARGS, getservbyname_doc}, {"getservbyport", socket_getservbyport, diff --git a/configure b/configure index 74d1ed41d2a..5f2a58f0b73 100755 --- a/configure +++ b/configure @@ -1,5 +1,5 @@ #! /bin/sh -# From configure.in Revision: 88624 . +# From configure.in Revision: 88625 . # Guess values for system-dependent variables and create Makefiles. # Generated by GNU Autoconf 2.65 for python 3.3. # @@ -9319,7 +9319,7 @@ for ac_func in alarm accept4 setitimer getitimer bind_textdomain_codeset chown \ mkfifoat mknod mknodat mktime mremap nice openat pathconf pause plock poll \ pthread_init putenv readlink readlinkat realpath renameat \ select sem_open sem_timedwait sem_getvalue sem_unlink sendfile setegid seteuid \ - setgid \ + setgid sethostname \ setlocale setregid setreuid setresuid setresgid setsid setpgid setpgrp setpriority setuid setvbuf \ sigaction siginterrupt sigrelse snprintf strftime strlcpy symlinkat \ sysconf tcgetpgrp tcsetpgrp tempnam timegm times tmpfile tmpnam tmpnam_r \ diff --git a/configure.in b/configure.in index 43e215933fa..5476250fecb 100644 --- a/configure.in +++ b/configure.in @@ -2542,7 +2542,7 @@ AC_CHECK_FUNCS(alarm accept4 setitimer getitimer bind_textdomain_codeset chown \ mkfifoat mknod mknodat mktime mremap nice openat pathconf pause plock poll \ pthread_init putenv readlink readlinkat realpath renameat \ select sem_open sem_timedwait sem_getvalue sem_unlink sendfile setegid seteuid \ - setgid \ + setgid sethostname \ setlocale setregid setreuid setresuid setresgid setsid setpgid setpgrp setpriority setuid setvbuf \ sigaction siginterrupt sigrelse snprintf strftime strlcpy symlinkat \ sysconf tcgetpgrp tcsetpgrp tempnam timegm times tmpfile tmpnam tmpnam_r \ diff --git a/pyconfig.h.in b/pyconfig.h.in index cfc84a550c3..3e6a1b5c41a 100644 --- a/pyconfig.h.in +++ b/pyconfig.h.in @@ -443,6 +443,9 @@ /* Define to 1 if you have the `resolv' library (-lresolv). */ #undef HAVE_LIBRESOLV +/* Define to 1 if you have the `sendfile' library (-lsendfile). */ +#undef HAVE_LIBSENDFILE + /* Define to 1 if you have the header file. */ #undef HAVE_LIBUTIL_H @@ -533,12 +536,6 @@ /* Define if the OS supports pipe2() */ #undef HAVE_PIPE2 -/* Define if the OS supports pipe2() */ -#undef HAVE_PIPE2 - -/* Define if the OS supports pipe2() */ -#undef HAVE_PIPE2 - /* Define to 1 if you have the `plock' function. */ #undef HAVE_PLOCK @@ -623,6 +620,9 @@ /* Define to 1 if you have the `sem_unlink' function. */ #undef HAVE_SEM_UNLINK +/* Define to 1 if you have the `sendfile' function. */ +#undef HAVE_SENDFILE + /* Define to 1 if you have the `setegid' function. */ #undef HAVE_SETEGID @@ -635,6 +635,9 @@ /* Define if you have the 'setgroups' function. */ #undef HAVE_SETGROUPS +/* Define to 1 if you have the `sethostname' function. */ +#undef HAVE_SETHOSTNAME + /* Define to 1 if you have the `setitimer' function. */ #undef HAVE_SETITIMER @@ -849,6 +852,9 @@ /* Define to 1 if you have the header file. */ #undef HAVE_SYS_TYPES_H +/* Define to 1 if you have the header file. */ +#undef HAVE_SYS_UIO_H + /* Define to 1 if you have the header file. */ #undef HAVE_SYS_UN_H @@ -1084,9 +1090,6 @@ /* The size of `size_t', as computed by sizeof. */ #undef SIZEOF_SIZE_T -/* Define to 1 if you have the `sendfile' function. */ -#undef HAVE_SENDFILE - /* The size of `time_t', as computed by sizeof. */ #undef SIZEOF_TIME_T