2 * Copyright 2009, Ingo Weinhold, ingo_weinhold@gmx.de.
3 * Distributed under the terms of the MIT License.
6 #include "SourceFile.h"
19 static const int32 kMaxSourceFileSize
= 10 * 1024 * 1024;
22 // #pragma mark - SourceFileOwner
25 SourceFileOwner::~SourceFileOwner()
30 // #pragma mark - SourceFile
33 SourceFile::SourceFile(SourceFileOwner
* owner
)
43 SourceFile::~SourceFile()
46 delete[] fLineOffsets
;
47 fOwner
->SourceFileDeleted(this);
52 SourceFile::Init(const char* path
)
55 int fd
= open(path
, O_RDONLY
);
59 // stat the file to get its size
61 if (fstat(fd
, &st
) < 0) {
66 if (st
.st_size
> kMaxSourceFileSize
) {
68 return B_FILE_TOO_LARGE
;
70 size_t fileSize
= st
.st_size
;
77 // allocate the content buffer
78 fFileContent
= (char*)malloc(fileSize
+ 1);
79 // one more byte for a terminating null
80 if (fFileContent
== NULL
) {
86 ssize_t bytesRead
= read(fd
, fFileContent
, fileSize
);
88 if (bytesRead
< 0 || (size_t)bytesRead
!= fileSize
)
89 return bytesRead
< 0 ? errno
: B_FILE_ERROR
;
92 fFileContent
[fileSize
] = '\0';
96 for (size_t i
= 0; i
< fileSize
; i
++) {
97 if (fFileContent
[i
] == '\n')
101 // allocate line offset array
102 fLineOffsets
= new(std::nothrow
) int32
[fLineCount
+ 1];
103 if (fLineOffsets
== NULL
)
106 // get the line offsets and null-terminate the lines
108 fLineOffsets
[lineIndex
++] = 0;
109 for (size_t i
= 0; i
< fileSize
; i
++) {
110 if (fFileContent
[i
] == '\n') {
111 fFileContent
[i
] = '\0';
112 fLineOffsets
[lineIndex
++] = i
+ 1;
115 fLineOffsets
[fLineCount
] = fileSize
+ 1;
122 SourceFile::CountLines() const
129 SourceFile::LineAt(int32 index
) const
131 return index
>= 0 && index
< fLineCount
132 ? fFileContent
+ fLineOffsets
[index
] : NULL
;
137 SourceFile::LineLengthAt(int32 index
) const
139 return index
>= 0 && index
< fLineCount
140 ? fLineOffsets
[index
+ 1] - fLineOffsets
[index
] - 1: 0;
144 SourceFile::LastReferenceReleased()
146 fOwner
->SourceFileUnused(this);