Home | History | Annotate | Download | only in test
      1 import unittest
      2 from test import test_support
      3 import time
      4 
      5 resource = test_support.import_module('resource')
      6 
      7 # This test is checking a few specific problem spots with the resource module.
      8 
      9 class ResourceTest(unittest.TestCase):
     10 
     11     def test_args(self):
     12         self.assertRaises(TypeError, resource.getrlimit)
     13         self.assertRaises(TypeError, resource.getrlimit, 42, 42)
     14         self.assertRaises(TypeError, resource.setrlimit)
     15         self.assertRaises(TypeError, resource.setrlimit, 42, 42, 42)
     16 
     17     def test_fsize_ismax(self):
     18         try:
     19             (cur, max) = resource.getrlimit(resource.RLIMIT_FSIZE)
     20         except AttributeError:
     21             pass
     22         else:
     23             # RLIMIT_FSIZE should be RLIM_INFINITY, which will be a really big
     24             # number on a platform with large file support.  On these platforms,
     25             # we need to test that the get/setrlimit functions properly convert
     26             # the number to a C long long and that the conversion doesn't raise
     27             # an error.
     28             self.assertEqual(resource.RLIM_INFINITY, max)
     29             resource.setrlimit(resource.RLIMIT_FSIZE, (cur, max))
     30 
     31     def test_fsize_enforced(self):
     32         try:
     33             (cur, max) = resource.getrlimit(resource.RLIMIT_FSIZE)
     34         except AttributeError:
     35             pass
     36         else:
     37             # Check to see what happens when the RLIMIT_FSIZE is small.  Some
     38             # versions of Python were terminated by an uncaught SIGXFSZ, but
     39             # pythonrun.c has been fixed to ignore that exception.  If so, the
     40             # write() should return EFBIG when the limit is exceeded.
     41 
     42             # At least one platform has an unlimited RLIMIT_FSIZE and attempts
     43             # to change it raise ValueError instead.
     44             try:
     45                 try:
     46                     resource.setrlimit(resource.RLIMIT_FSIZE, (1024, max))
     47                     limit_set = True
     48                 except ValueError:
     49                     limit_set = False
     50                 f = open(test_support.TESTFN, "wb")
     51                 try:
     52                     f.write("X" * 1024)
     53                     try:
     54                         f.write("Y")
     55                         f.flush()
     56                         # On some systems (e.g., Ubuntu on hppa) the flush()
     57                         # doesn't always cause the exception, but the close()
     58                         # does eventually.  Try flushing several times in
     59                         # an attempt to ensure the file is really synced and
     60                         # the exception raised.
     61                         for i in range(5):
     62                             time.sleep(.1)
     63                             f.flush()
     64                     except IOError:
     65                         if not limit_set:
     66                             raise
     67                     if limit_set:
     68                         # Close will attempt to flush the byte we wrote
     69                         # Restore limit first to avoid getting a spurious error
     70                         resource.setrlimit(resource.RLIMIT_FSIZE, (cur, max))
     71                 finally:
     72                     f.close()
     73             finally:
     74                 if limit_set:
     75                     resource.setrlimit(resource.RLIMIT_FSIZE, (cur, max))
     76                 test_support.unlink(test_support.TESTFN)
     77 
     78     def test_fsize_toobig(self):
     79         # Be sure that setrlimit is checking for really large values
     80         too_big = 10L**50
     81         try:
     82             (cur, max) = resource.getrlimit(resource.RLIMIT_FSIZE)
     83         except AttributeError:
     84             pass
     85         else:
     86             try:
     87                 resource.setrlimit(resource.RLIMIT_FSIZE, (too_big, max))
     88             except (OverflowError, ValueError):
     89                 pass
     90             try:
     91                 resource.setrlimit(resource.RLIMIT_FSIZE, (max, too_big))
     92             except (OverflowError, ValueError):
     93                 pass
     94 
     95     def test_getrusage(self):
     96         self.assertRaises(TypeError, resource.getrusage)
     97         self.assertRaises(TypeError, resource.getrusage, 42, 42)
     98         usageself = resource.getrusage(resource.RUSAGE_SELF)
     99         usagechildren = resource.getrusage(resource.RUSAGE_CHILDREN)
    100         # May not be available on all systems.
    101         try:
    102             usageboth = resource.getrusage(resource.RUSAGE_BOTH)
    103         except (ValueError, AttributeError):
    104             pass
    105 
    106     # Issue 6083: Reference counting bug
    107     def test_setrusage_refcount(self):
    108         try:
    109             limits = resource.getrlimit(resource.RLIMIT_CPU)
    110         except AttributeError:
    111             pass
    112         else:
    113             class BadSequence:
    114                 def __len__(self):
    115                     return 2
    116                 def __getitem__(self, key):
    117                     if key in (0, 1):
    118                         return len(tuple(range(1000000)))
    119                     raise IndexError
    120 
    121             resource.setrlimit(resource.RLIMIT_CPU, BadSequence())
    122 
    123 def test_main(verbose=None):
    124     test_support.run_unittest(ResourceTest)
    125 
    126 if __name__ == "__main__":
    127     test_main()
    128