]> err.no Git - sope/blob - libFoundation/Foundation/NSMappedData.m
Drop apache 1 build-dependency
[sope] / libFoundation / Foundation / NSMappedData.m
1 /* 
2    NSMappedData.m
3
4    Copyright (C) 1995, 1996 Ovidiu Predescu and Mircea Oancea.
5    All rights reserved.
6
7    Author: Mircea Oancea <mircea@jupiter.elcom.pub.ro>
8
9    This file is part of libFoundation.
10
11    Permission to use, copy, modify, and distribute this software and its
12    documentation for any purpose and without fee is hereby granted, provided
13    that the above copyright notice appear in all copies and that both that
14    copyright notice and this permission notice appear in supporting
15    documentation.
16
17    We disclaim all warranties with regard to this software, including all
18    implied warranties of merchantability and fitness, in no event shall
19    we be liable for any special, indirect or consequential damages or any
20    damages whatsoever resulting from loss of use, data or profits, whether in
21    an action of contract, negligence or other tortious action, arising out of
22    or in connection with the use or performance of this software.
23 */
24
25 #include <Foundation/common.h>
26 #include <Foundation/NSPosixFileDescriptor.h>
27 #include <Foundation/NSException.h>
28 #include <Foundation/exceptions/GeneralExceptions.h>
29
30 #ifdef NeXT /* NeXT Mach map_fd() */
31 # include <mach/mach.h>
32 # include <libc.h>
33 #elif defined(HAVE_MMAP) /* Posix mmap() */
34 #  include <sys/types.h>
35 #  include <sys/mman.h>
36 #  include <unistd.h>
37 #else  /* No file mapping available */
38 #endif
39
40 #include "NSMappedData.h"
41
42 /*
43  * Read-only mapped data
44  */
45
46 @implementation NSMappedData
47
48 - (id)initWithPosixFileDescriptor:(NSPosixFileDescriptor*)descriptor
49   range:(NSRange)range
50 {
51     file = RETAIN(descriptor);
52
53     if (range.location + range.length > [file fileLength])
54         [[[RangeException alloc]
55                 initWithReason:@"invalid range to be mapped" 
56                 size:[file fileLength] 
57                 index:range.location+range.length] raise];
58
59     length = capacity = range.length;
60     [file seekToPosition:range.location];
61
62     if (!length)
63         return self;
64
65 #ifdef NeXT     
66     /* NeXt Mach map_fd() */
67     {
68         kern_return_t r;
69
70         r = map_fd([file fileDescriptor], (vm_offset_t)0, 
71             (vm_offset_t*)(&bytes), TRUE, (vm_size_t)length);
72         if (r != KERN_SUCCESS) {
73             bytes = NULL;
74             AUTORELEASE(self);
75             return nil;
76         }
77         return self;
78     }
79 #elif defined(HAVE_MMAP)
80     /* Posix mmap() */
81     {
82         bytes = mmap(0, length, PROT_READ, MAP_SHARED,
83                      [file fileDescriptor], 0);
84         if ((long)bytes == -1L) {
85             bytes = NULL;
86             (void)AUTORELEASE(self);
87             return nil;
88         }
89         return self;
90     }
91 #else   
92     /* No file mapping available */
93     {
94         bytes = MallocAtomic (length);
95         [file readBytes:bytes range:range];
96         return self;
97     }
98 #endif
99 }
100
101 - (void)dealloc
102 {
103 #ifdef NeXT     
104     /* NeXt Mach map_fd() */
105     if (bytes && length)
106         vm_deallocate(task_self(), (vm_address_t)bytes, length);
107 #elif defined(HAVE_MMAP)
108     /* Posix mmap() */
109     if (bytes && length)
110         munmap(bytes, length);
111 #else   
112     /* No file mapping available */
113     lfFree(bytes);
114 #endif
115     RELEASE(file);
116     [super dealloc];
117 }
118
119 - (id)copyWithZone:(NSZone*)zone
120 {
121     return RETAIN(self);
122 }
123
124 - (const void*)bytes
125 {
126     return bytes;
127 }
128
129 - (unsigned int)length
130 {
131     return length;
132 }
133
134 @end /* NSMappedData */
135 /*
136   Local Variables:
137   c-basic-offset: 4
138   tab-width: 8
139   End:
140 */
141