--- daemon/daemon.c	2008-12-30 10:48:17.000000000 +0100
+++ daemon/daemon.c	2008-12-30 10:54:36.000000000 +0100
@@ -16,6 +16,9 @@
 #include <stdlib.h> /* exit, atoi */
 #include <string.h> /* strcmp */
 
+#include <sys/types.h> /* umask*/
+#include <sys/stat.h> /* umask*/
+
 #include <fcntl.h> /* open */
 #include <signal.h>
 #include <unistd.h> /* daemon */
@@ -360,82 +363,62 @@
     closing = TRUE;
 }
 
-#if !defined( WIN32 )
-#if !defined( HAVE_DAEMON )
+#if defined(WIN32)
+ #define USE_NO_DAEMON
+#elif !defined(HAVE_DAEMON) || defined(__MIPSEL__)
+ #define USE_TR_DAEMON
+#else
+ #define USE_OS_DAEMON
+#endif
+
 static int
-daemon( int nochdir,
-        int noclose )
+tr_daemon( int nochdir, int noclose )
 {
-    switch( fork( ) )
-    {
-        case 0:
-            break;
-
-        case - 1:
-            tr_nerr( MY_NAME, "Error daemonizing (fork)! %d - %s", errno,
-                    strerror(
-                        errno ) );
-            return -1;
-
-        default:
-            _exit( 0 );
-    }
-
-    if( setsid( ) < 0 )
-    {
-        tr_nerr( MY_NAME, "Error daemonizing (setsid)! %d - %s", errno,
-                strerror(
-                    errno ) );
+#if defined(USE_OS_DAEMON)
+    return daemon( nochdir, noclose );
+#elif defined(USE_TR_DAEMON)
+    pid_t pid = fork( );
+    if( pid < 0 )
         return -1;
-    }
-
-    switch( fork( ) )
-    {
-        case 0:
-            break;
-
-        case - 1:
-            tr_nerr( MY_NAME, "Error daemonizing (fork2)! %d - %s", errno,
-                    strerror(
-                        errno ) );
+    else if( pid > 0 )
+        _exit( 0 );
+    else {
+        pid = setsid( );
+        if( pid < 0 )
             return -1;
 
-        default:
+        pid = fork( );
+        if( pid < 0 )
+            return -1;
+        else if( pid > 0 )
             _exit( 0 );
-    }
+        else {
 
-    if( !nochdir && 0 > chdir( "/" ) )
-    {
-        tr_nerr( MY_NAME, "Error daemonizing (chdir)! %d - %s", errno,
-                strerror(
-                    errno ) );
-        return -1;
-    }
+            if( !nochdir )
+                if( chdir( "/" ) < 0 )
+                    return -1;
+
+            umask( (mode_t)0 );
+
+            if( !noclose ) {
+                /* send stdin, stdout, and stderr to /dev/null */
+                int i;
+                int fd = open( "/dev/null", O_RDWR, 0 );
+                for( i=0; i<3; ++i ) {
+                    if( close( i ) )
+                        return -1;
+                    dup2( fd, i );
+                }
+                close( fd );
+            }
 
-    if( !noclose )
-    {
-        int fd;
-        if( ( ( fd = open( "/dev/null", O_RDONLY ) ) ) != 0 )
-        {
-            dup2( fd,  0 );
-            close( fd );
-        }
-        if( ( ( fd = open( "/dev/null", O_WRONLY ) ) ) != 1 )
-        {
-            dup2( fd, 1 );
-            close( fd );
-        }
-        if( ( ( fd = open( "/dev/null", O_WRONLY ) ) ) != 2 )
-        {
-            dup2( fd, 2 );
-            close( fd );
+            return 0;
         }
     }
-
+#else /* USE_NO_DAEMON */
     return 0;
-}
-#endif
 #endif
+}
 
 int
 main( int     argc,
@@ -470,16 +453,11 @@
                                                tr_getDefaultConfigDir( ) );
     myConfigFilename = tr_buildPath( configDir, CONFIG_FILE, NULL );
 
-#ifndef WIN32
-    if( !nofork )
+    if( !nofork && tr_daemon( TRUE, FALSE ) < 0 )
     {
-        if( 0 > daemon( 1, 0 ) )
-        {
-            fprintf( stderr, "failed to daemonize: %s\n", strerror( errno ) );
-            exit( 1 );
-        }
+        fprintf( stderr, "failed to daemonize: %s\n", strerror( errno ) );
+        exit( 1 );
     }
-#endif
 
     session_init( configDir, downloadDir,
                   rpcPort, whitelist, authRequired, username, password,
