vfs: check userland buffers before reading them.
[haiku.git] / src / kits / debugger / jobs / LoadImageDebugInfoJob.cpp
blobd576f08fb2f41bf45abceb3ded70346e22d138aa
1 /*
2 * Copyright 2012-2014, Rene Gollent, rene@gollent.com.
3 * Copyright 2009, Ingo Weinhold, ingo_weinhold@gmx.de.
4 * Distributed under the terms of the MIT License.
5 */
7 #include "Jobs.h"
9 #include <AutoLocker.h>
11 #include "Image.h"
12 #include "ImageDebugInfo.h"
13 #include "TeamDebugInfo.h"
14 #include "Team.h"
17 // #pragma mark - LoadImageDebugInfoJob
20 LoadImageDebugInfoJob::LoadImageDebugInfoJob(Image* image)
22 fKey(image, JOB_TYPE_LOAD_IMAGE_DEBUG_INFO),
23 fImage(image),
24 fState()
26 fImage->AcquireReference();
28 SetDescription("Loading debugging information for %s",
29 fImage->Name().String());
33 LoadImageDebugInfoJob::~LoadImageDebugInfoJob()
35 fImage->ReleaseReference();
39 const JobKey&
40 LoadImageDebugInfoJob::Key() const
42 return fKey;
46 status_t
47 LoadImageDebugInfoJob::Do()
49 // get an image info for the image
50 AutoLocker<Team> locker(fImage->GetTeam());
51 ImageInfo imageInfo(fImage->Info());
52 locker.Unlock();
54 // create the debug info
55 ImageDebugInfo* debugInfo;
56 status_t error = fImage->GetTeam()->DebugInfo()->LoadImageDebugInfo(
57 imageInfo, fImage->ImageFile(), fState, debugInfo);
59 // set the result
60 locker.Lock();
62 if (fState.UserInputRequired()) {
63 return WaitForUserInput();
64 } else if (error == B_OK) {
65 error = fImage->SetImageDebugInfo(debugInfo, IMAGE_DEBUG_INFO_LOADED);
66 debugInfo->ReleaseReference();
67 } else
68 fImage->SetImageDebugInfo(NULL, IMAGE_DEBUG_INFO_UNAVAILABLE);
70 return error;
74 /*static*/ status_t
75 LoadImageDebugInfoJob::ScheduleIfNecessary(Worker* worker, Image* image,
76 JobListener* listener, ImageDebugInfo** _imageDebugInfo)
78 AutoLocker<Team> teamLocker(image->GetTeam());
80 // If already loaded, we're done.
81 if (image->GetImageDebugInfo() != NULL) {
82 if (_imageDebugInfo != NULL) {
83 *_imageDebugInfo = image->GetImageDebugInfo();
84 (*_imageDebugInfo)->AcquireReference();
86 return B_OK;
89 // If already loading, the caller has to wait, if desired.
90 if (image->ImageDebugInfoState() == IMAGE_DEBUG_INFO_LOADING) {
91 if (_imageDebugInfo != NULL)
92 *_imageDebugInfo = NULL;
93 return B_OK;
96 // If an earlier load attempt failed, bail out.
97 if (image->ImageDebugInfoState() != IMAGE_DEBUG_INFO_NOT_LOADED)
98 return B_ERROR;
100 // schedule a job
101 LoadImageDebugInfoJob* job = new(std::nothrow) LoadImageDebugInfoJob(
102 image);
103 if (job == NULL)
104 return B_NO_MEMORY;
106 status_t error = worker->ScheduleJob(job, listener);
107 if (error != B_OK) {
108 image->SetImageDebugInfo(NULL, IMAGE_DEBUG_INFO_UNAVAILABLE);
109 return error;
112 image->SetImageDebugInfo(NULL, IMAGE_DEBUG_INFO_LOADING);
114 if (_imageDebugInfo != NULL)
115 *_imageDebugInfo = NULL;
116 return B_OK;