* Completed image tracking using the image event counter sent with
various debugger messages. We do now correctly match all sampled addresses. * Update the saved info of a team's main thread after exec*(), so we can print a more useful name. * Improved the output: The images are listed in a table, now. The function table also includes the image IDs for the functions. * Cleaned up debug output. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@27657 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
+221
-62
@@ -80,11 +80,13 @@ struct HitSymbol {
|
|||||||
|
|
||||||
class Image : public Referenceable {
|
class Image : public Referenceable {
|
||||||
public:
|
public:
|
||||||
Image(const image_info& info)
|
Image(const image_info& info, int32 creationEvent)
|
||||||
:
|
:
|
||||||
fInfo(info),
|
fInfo(info),
|
||||||
fSymbols(NULL),
|
fSymbols(NULL),
|
||||||
fSymbolCount(0)
|
fSymbolCount(0),
|
||||||
|
fCreationEvent(creationEvent),
|
||||||
|
fDeletionEvent(-1)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -107,10 +109,25 @@ public:
|
|||||||
return fInfo;
|
return fInfo;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int32 CreationEvent() const
|
||||||
|
{
|
||||||
|
return fCreationEvent;
|
||||||
|
}
|
||||||
|
|
||||||
|
int32 DeletionEvent() const
|
||||||
|
{
|
||||||
|
return fDeletionEvent;
|
||||||
|
}
|
||||||
|
|
||||||
|
void SetDeletionEvent(int32 event)
|
||||||
|
{
|
||||||
|
fDeletionEvent = event;
|
||||||
|
}
|
||||||
|
|
||||||
status_t LoadSymbols(debug_symbol_lookup_context* lookupContext)
|
status_t LoadSymbols(debug_symbol_lookup_context* lookupContext)
|
||||||
{
|
{
|
||||||
printf("Loading symbols of image \"%s\" (%ld)...\n", fInfo.name,
|
// printf("Loading symbols of image \"%s\" (%ld)...\n", fInfo.name,
|
||||||
fInfo.id);
|
// fInfo.id);
|
||||||
|
|
||||||
// create symbol iterator
|
// create symbol iterator
|
||||||
debug_symbol_iterator* iterator;
|
debug_symbol_iterator* iterator;
|
||||||
@@ -203,6 +220,8 @@ private:
|
|||||||
image_info fInfo;
|
image_info fInfo;
|
||||||
Symbol** fSymbols;
|
Symbol** fSymbols;
|
||||||
int32 fSymbolCount;
|
int32 fSymbolCount;
|
||||||
|
int32 fCreationEvent;
|
||||||
|
int32 fDeletionEvent;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
@@ -316,6 +335,13 @@ public:
|
|||||||
addr_t* Samples() const { return fSamples; }
|
addr_t* Samples() const { return fSamples; }
|
||||||
Team* GetTeam() const { return fTeam; }
|
Team* GetTeam() const { return fTeam; }
|
||||||
|
|
||||||
|
void UpdateInfo()
|
||||||
|
{
|
||||||
|
thread_info info;
|
||||||
|
if (get_thread_info(ID(), &info) == B_OK)
|
||||||
|
fInfo = info;
|
||||||
|
}
|
||||||
|
|
||||||
void SetSampleArea(area_id area, addr_t* samples)
|
void SetSampleArea(area_id area, addr_t* samples)
|
||||||
{
|
{
|
||||||
fSampleArea = area;
|
fSampleArea = area;
|
||||||
@@ -369,8 +395,21 @@ public:
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
void AddSamples(int32 count, int32 stackDepth)
|
void AddSamples(int32 count, int32 stackDepth, int32 event)
|
||||||
{
|
{
|
||||||
|
_RemoveObsoleteImages(event);
|
||||||
|
|
||||||
|
// Temporarily remove images that have been created after the given
|
||||||
|
// event.
|
||||||
|
ImageList newImages;
|
||||||
|
ImageList::Iterator it = fImages.GetIterator();
|
||||||
|
while (ThreadImage* image = it.Next()) {
|
||||||
|
if (image->GetImage()->CreationEvent() > event) {
|
||||||
|
it.Remove();
|
||||||
|
newImages.Add(image);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
count = count / stackDepth * stackDepth;
|
count = count / stackDepth * stackDepth;
|
||||||
|
|
||||||
for (int32 i = 0; i < count; i += stackDepth) {
|
for (int32 i = 0; i < count; i += stackDepth) {
|
||||||
@@ -389,37 +428,68 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
fTotalHits += count / stackDepth;
|
fTotalHits += count / stackDepth;
|
||||||
|
|
||||||
|
// re-add the new images
|
||||||
|
fImages.MoveFrom(&newImages);
|
||||||
|
|
||||||
|
_SynchronizeImages();
|
||||||
}
|
}
|
||||||
|
|
||||||
void PrintResults() const
|
void PrintResults() const
|
||||||
{
|
{
|
||||||
printf("total hits: %lld, missed: %lld\n", fTotalHits, fMissedTicks);
|
// count images and symbols
|
||||||
|
int32 imageCount = 0;
|
||||||
int32 symbolCount = 0;
|
int32 symbolCount = 0;
|
||||||
|
|
||||||
ImageList::ConstIterator it = fImages.GetIterator();
|
ImageList::ConstIterator it = fOldImages.GetIterator();
|
||||||
while (ThreadImage* image = it.Next()) {
|
while (ThreadImage* image = it.Next()) {
|
||||||
const image_info& imageInfo = image->GetImage()->Info();
|
if (image->TotalHits() > 0) {
|
||||||
printf(" image: %s (%ld): %lld hits, %lld misses\n",
|
imageCount++;
|
||||||
imageInfo.name, imageInfo.id, image->TotalHits(),
|
if (image->TotalHits() > image->MissedHits())
|
||||||
image->MissedHits());
|
symbolCount += image->GetImage()->SymbolCount();
|
||||||
symbolCount += image->GetImage()->SymbolCount();
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
it = fImages.GetIterator();
|
||||||
|
while (ThreadImage* image = it.Next()) {
|
||||||
|
if (image->TotalHits() > 0) {
|
||||||
|
imageCount++;
|
||||||
|
if (image->TotalHits() > image->MissedHits())
|
||||||
|
symbolCount += image->GetImage()->SymbolCount();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ThreadImage* images[imageCount];
|
||||||
|
imageCount = 0;
|
||||||
|
|
||||||
|
it = fOldImages.GetIterator();
|
||||||
|
while (ThreadImage* image = it.Next()) {
|
||||||
|
if (image->TotalHits() > 0)
|
||||||
|
images[imageCount++] = image;
|
||||||
|
}
|
||||||
|
|
||||||
|
it = fImages.GetIterator();
|
||||||
|
while (ThreadImage* image = it.Next()) {
|
||||||
|
if (image->TotalHits() > 0)
|
||||||
|
images[imageCount++] = image;
|
||||||
}
|
}
|
||||||
|
|
||||||
// find and sort the hit symbols
|
// find and sort the hit symbols
|
||||||
HitSymbol hitSymbols[symbolCount];
|
HitSymbol hitSymbols[symbolCount];
|
||||||
int32 hitSymbolCount = 0;
|
int32 hitSymbolCount = 0;
|
||||||
|
|
||||||
it = fImages.GetIterator();
|
for (int32 k = 0; k < imageCount; k++) {
|
||||||
while (ThreadImage* image = it.Next()) {
|
ThreadImage* image = images[k];
|
||||||
Symbol** symbols = image->GetImage()->Symbols();
|
if (image->TotalHits() > image->MissedHits()) {
|
||||||
const int64* symbolHits = image->SymbolHits();
|
Symbol** symbols = image->GetImage()->Symbols();
|
||||||
int32 imageSymbolCount = image->GetImage()->SymbolCount();
|
const int64* symbolHits = image->SymbolHits();
|
||||||
for (int32 i = 0; i < imageSymbolCount; i++) {
|
int32 imageSymbolCount = image->GetImage()->SymbolCount();
|
||||||
if (symbolHits[i] > 0) {
|
for (int32 i = 0; i < imageSymbolCount; i++) {
|
||||||
HitSymbol& hitSymbol = hitSymbols[hitSymbolCount++];
|
if (symbolHits[i] > 0) {
|
||||||
hitSymbol.hits = symbolHits[i];
|
HitSymbol& hitSymbol = hitSymbols[hitSymbolCount++];
|
||||||
hitSymbol.symbol = symbols[i];
|
hitSymbol.hits = symbolHits[i];
|
||||||
|
hitSymbol.symbol = symbols[i];
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -438,18 +508,30 @@ public:
|
|||||||
fMissedTicks, fMissedTicks * fInterval,
|
fMissedTicks, fMissedTicks * fInterval,
|
||||||
100.0 * fMissedTicks / totalTicks);
|
100.0 * fMissedTicks / totalTicks);
|
||||||
|
|
||||||
|
if (imageCount > 0) {
|
||||||
|
printf("\n");
|
||||||
|
printf(" hits unknown image\n");
|
||||||
|
printf(" -------------------------------------------------"
|
||||||
|
"-----------------------------\n");
|
||||||
|
for (int32 k = 0; k < imageCount; k++) {
|
||||||
|
ThreadImage* image = images[k];
|
||||||
|
const image_info& imageInfo = image->GetImage()->Info();
|
||||||
|
printf(" %10lld %10lld %7ld %s\n", image->TotalHits(),
|
||||||
|
image->MissedHits(), imageInfo.id, imageInfo.name);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (hitSymbolCount > 0) {
|
if (hitSymbolCount > 0) {
|
||||||
printf("\n");
|
printf("\n");
|
||||||
printf(" hits in us in %% function\n");
|
printf(" hits in us in %% image function\n");
|
||||||
printf(" -------------------------------------------------"
|
printf(" -------------------------------------------------"
|
||||||
"-----------------------------\n");
|
"-----------------------------\n");
|
||||||
for (int32 i = 0; i < hitSymbolCount; i++) {
|
for (int32 i = 0; i < hitSymbolCount; i++) {
|
||||||
const HitSymbol& hitSymbol = hitSymbols[i];
|
const HitSymbol& hitSymbol = hitSymbols[i];
|
||||||
const Symbol* symbol = hitSymbol.symbol;
|
const Symbol* symbol = hitSymbol.symbol;
|
||||||
printf(" %10lld %10lld %6.2f %s\n", hitSymbol.hits,
|
printf(" %10lld %10lld %6.2f %6ld %s\n", hitSymbol.hits,
|
||||||
hitSymbol.hits * fInterval,
|
hitSymbol.hits * fInterval,
|
||||||
100.0 * hitSymbol.hits / totalTicks,
|
100.0 * hitSymbol.hits / totalTicks, symbol->image->ID(),
|
||||||
symbol->Name());
|
symbol->Name());
|
||||||
}
|
}
|
||||||
} else
|
} else
|
||||||
@@ -457,9 +539,38 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
typedef DoublyLinkedList<ThreadImage> ImageList;
|
void _SynchronizeImages();
|
||||||
|
|
||||||
|
void _RemoveObsoleteImages(int32 event)
|
||||||
|
{
|
||||||
|
// remove obsolete images
|
||||||
|
ImageList::Iterator it = fImages.GetIterator();
|
||||||
|
while (ThreadImage* image = it.Next()) {
|
||||||
|
int32 deleted = image->GetImage()->DeletionEvent();
|
||||||
|
if (deleted >= 0 && event >= deleted) {
|
||||||
|
it.Remove();
|
||||||
|
if (image->TotalHits() > 0)
|
||||||
|
fOldImages.Add(image);
|
||||||
|
else
|
||||||
|
delete image;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ThreadImage* _FindImageByID(image_id id) const
|
||||||
|
{
|
||||||
|
ImageList::ConstIterator it = fImages.GetIterator();
|
||||||
|
while (ThreadImage* image = it.Next()) {
|
||||||
|
if (image->ID() == id)
|
||||||
|
return image;
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
typedef DoublyLinkedList<ThreadImage> ImageList;
|
||||||
|
|
||||||
thread_info fInfo;
|
thread_info fInfo;
|
||||||
::Team* fTeam;
|
::Team* fTeam;
|
||||||
area_id fSampleArea;
|
area_id fSampleArea;
|
||||||
@@ -595,7 +706,6 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
thread->SetInterval(reply.interval);
|
thread->SetInterval(reply.interval);
|
||||||
//reply.profile_event
|
|
||||||
|
|
||||||
fThreads.Add(thread);
|
fThreads.Add(thread);
|
||||||
|
|
||||||
@@ -610,15 +720,24 @@ public:
|
|||||||
fThreads.Remove(thread);
|
fThreads.Remove(thread);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Exec()
|
void Exec(int32 event)
|
||||||
{
|
{
|
||||||
// remove all images
|
// remove all images
|
||||||
int32 imageCount = fImages.CountItems();
|
int32 imageCount = fImages.CountItems();
|
||||||
for (int32 i = imageCount - 1; i >= 0; i--)
|
for (int32 i = imageCount - 1; i >= 0; i--)
|
||||||
_RemoveImage(i);
|
_RemoveImage(i, event);
|
||||||
|
|
||||||
|
// update the main thread
|
||||||
|
ThreadList::Iterator it = fThreads.GetIterator();
|
||||||
|
while (Thread* thread = it.Next()) {
|
||||||
|
if (thread->ID() == ID()) {
|
||||||
|
thread->UpdateInfo();
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
status_t AddImage(const image_info& imageInfo)
|
status_t AddImage(const image_info& imageInfo, int32 event)
|
||||||
{
|
{
|
||||||
// create symbol lookup context
|
// create symbol lookup context
|
||||||
debug_symbol_lookup_context* lookupContext;
|
debug_symbol_lookup_context* lookupContext;
|
||||||
@@ -631,24 +750,26 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
Image* image;
|
Image* image;
|
||||||
error = _LoadImageSymbols(lookupContext, imageInfo, &image);
|
error = _LoadImageSymbols(lookupContext, imageInfo, event, &image);
|
||||||
debug_delete_symbol_lookup_context(lookupContext);
|
debug_delete_symbol_lookup_context(lookupContext);
|
||||||
|
|
||||||
// TODO: Remove! The threads must be updated lazily.
|
// Although we generally synchronize the threads' images lazily, we have
|
||||||
if (error == B_OK) {
|
// to add new images at least, since otherwise images could be added
|
||||||
ThreadList::Iterator it = fThreads.GetIterator();
|
// and removed again, and the hits inbetween could never be matched.
|
||||||
while (Thread* thread = it.Next())
|
if (error == B_OK) {
|
||||||
thread->AddImage(image);
|
ThreadList::Iterator it = fThreads.GetIterator();
|
||||||
}
|
while (Thread* thread = it.Next())
|
||||||
|
thread->AddImage(image);
|
||||||
|
}
|
||||||
|
|
||||||
return error;
|
return error;
|
||||||
}
|
}
|
||||||
|
|
||||||
status_t RemoveImage(const image_info& imageInfo)
|
status_t RemoveImage(const image_info& imageInfo, int32 event)
|
||||||
{
|
{
|
||||||
for (int32 i = 0; Image* image = fImages.ItemAt(i); i++) {
|
for (int32 i = 0; Image* image = fImages.ItemAt(i); i++) {
|
||||||
if (image->ID() == imageInfo.id) {
|
if (image->ID() == imageInfo.id) {
|
||||||
_RemoveImage(i);
|
_RemoveImage(i, event);
|
||||||
return B_OK;
|
return B_OK;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -656,6 +777,21 @@ if (error == B_OK) {
|
|||||||
return B_ENTRY_NOT_FOUND;
|
return B_ENTRY_NOT_FOUND;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const BObjectList<Image>& Images() const
|
||||||
|
{
|
||||||
|
return fImages;
|
||||||
|
}
|
||||||
|
|
||||||
|
Image* FindImage(image_id id) const
|
||||||
|
{
|
||||||
|
for (int32 i = 0; Image* image = fImages.ItemAt(i); i++) {
|
||||||
|
if (image->ID() == id)
|
||||||
|
return image;
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
team_id ID() const
|
team_id ID() const
|
||||||
{
|
{
|
||||||
return fInfo.team;
|
return fInfo.team;
|
||||||
@@ -668,7 +804,7 @@ private:
|
|||||||
image_info imageInfo;
|
image_info imageInfo;
|
||||||
int32 cookie = 0;
|
int32 cookie = 0;
|
||||||
while (get_next_image_info(fInfo.team, &cookie, &imageInfo) == B_OK) {
|
while (get_next_image_info(fInfo.team, &cookie, &imageInfo) == B_OK) {
|
||||||
status_t error = _LoadImageSymbols(lookupContext, imageInfo);
|
status_t error = _LoadImageSymbols(lookupContext, imageInfo, 0);
|
||||||
if (error == B_NO_MEMORY)
|
if (error == B_NO_MEMORY)
|
||||||
return error;
|
return error;
|
||||||
}
|
}
|
||||||
@@ -677,9 +813,9 @@ private:
|
|||||||
}
|
}
|
||||||
|
|
||||||
status_t _LoadImageSymbols(debug_symbol_lookup_context* lookupContext,
|
status_t _LoadImageSymbols(debug_symbol_lookup_context* lookupContext,
|
||||||
const image_info& imageInfo, Image** _image = NULL)
|
const image_info& imageInfo, int32 event, Image** _image = NULL)
|
||||||
{
|
{
|
||||||
Image* image = new(std::nothrow) Image(imageInfo);
|
Image* image = new(std::nothrow) Image(imageInfo, event);
|
||||||
if (image == NULL)
|
if (image == NULL)
|
||||||
return B_NO_MEMORY;
|
return B_NO_MEMORY;
|
||||||
|
|
||||||
@@ -700,17 +836,18 @@ private:
|
|||||||
return B_OK;
|
return B_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
void _RemoveImage(int32 index)
|
void _RemoveImage(int32 index, int32 event)
|
||||||
{
|
{
|
||||||
Image* image = fImages.RemoveItemAt(index);
|
Image* image = fImages.RemoveItemAt(index);
|
||||||
if (image == NULL)
|
if (image == NULL)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
// notify all threads that the image has been removed
|
// Note: We don't tell the threads that the image has been removed. They
|
||||||
ThreadList::Iterator it = fThreads.GetIterator();
|
// will be updated lazily when their next profiler update arrives. This
|
||||||
while (Thread* thread = it.Next())
|
// is necessary, since the update might contain samples hitting that
|
||||||
thread->ImageRemoved(image);
|
// image.
|
||||||
|
|
||||||
|
image->SetDeletionEvent(event);
|
||||||
image->RemoveReference();
|
image->RemoveReference();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -825,6 +962,31 @@ private:
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
void
|
||||||
|
Thread::_SynchronizeImages()
|
||||||
|
{
|
||||||
|
const BObjectList<Image>& teamImages = fTeam->Images();
|
||||||
|
|
||||||
|
// remove obsolete images
|
||||||
|
ImageList::Iterator it = fImages.GetIterator();
|
||||||
|
while (ThreadImage* image = it.Next()) {
|
||||||
|
if (fTeam->FindImage(image->ID()) == NULL) {
|
||||||
|
it.Remove();
|
||||||
|
if (image->TotalHits() > 0)
|
||||||
|
fOldImages.Add(image);
|
||||||
|
else
|
||||||
|
delete image;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// add new images
|
||||||
|
for (int32 i = 0; Image* image = teamImages.ItemAt(i); i++) {
|
||||||
|
if (_FindImageByID(image->ID()) == NULL)
|
||||||
|
AddImage(image);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// TODO: Adjust!
|
// TODO: Adjust!
|
||||||
static const char* kUsage =
|
static const char* kUsage =
|
||||||
"Usage: %s [ <options> ] <command line>\n"
|
"Usage: %s [ <options> ] <command line>\n"
|
||||||
@@ -974,7 +1136,8 @@ main(int argc, const char* const* argv)
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
thread->AddSamples(message.profiler_update.sample_count,
|
thread->AddSamples(message.profiler_update.sample_count,
|
||||||
message.profiler_update.stack_depth);
|
message.profiler_update.stack_depth,
|
||||||
|
message.profiler_update.image_event);
|
||||||
|
|
||||||
if (message.profiler_update.stopped) {
|
if (message.profiler_update.stopped) {
|
||||||
thread->PrintResults();
|
thread->PrintResults();
|
||||||
@@ -995,7 +1158,7 @@ main(int argc, const char* const* argv)
|
|||||||
break;
|
break;
|
||||||
case B_DEBUGGER_MESSAGE_TEAM_EXEC:
|
case B_DEBUGGER_MESSAGE_TEAM_EXEC:
|
||||||
if (Team* team = threadManager.FindTeam(message.origin.team))
|
if (Team* team = threadManager.FindTeam(message.origin.team))
|
||||||
team->Exec();
|
team->Exec(message.team_exec.image_event);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case B_DEBUGGER_MESSAGE_THREAD_CREATED:
|
case B_DEBUGGER_MESSAGE_THREAD_CREATED:
|
||||||
@@ -1006,21 +1169,17 @@ main(int argc, const char* const* argv)
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case B_DEBUGGER_MESSAGE_IMAGE_CREATED:
|
case B_DEBUGGER_MESSAGE_IMAGE_CREATED:
|
||||||
{
|
if (Team* team = threadManager.FindTeam(message.origin.team)) {
|
||||||
const image_info& info = message.image_created.info;
|
team->AddImage(message.image_created.info,
|
||||||
printf("B_DEBUGGER_MESSAGE_IMAGE_CREATED: %s (%ld)\n", info.name, info.id);
|
message.image_created.image_event);
|
||||||
if (Team* team = threadManager.FindTeam(message.origin.team))
|
}
|
||||||
team->AddImage(message.image_created.info);
|
|
||||||
break;
|
break;
|
||||||
}
|
|
||||||
case B_DEBUGGER_MESSAGE_IMAGE_DELETED:
|
case B_DEBUGGER_MESSAGE_IMAGE_DELETED:
|
||||||
{
|
if (Team* team = threadManager.FindTeam(message.origin.team)) {
|
||||||
const image_info& info = message.image_deleted.info;
|
team->RemoveImage(message.image_deleted.info,
|
||||||
printf("B_DEBUGGER_MESSAGE_IMAGE_DELETED: %s (%ld)\n", info.name, info.id);
|
message.image_deleted.image_event);
|
||||||
if (Team* team = threadManager.FindTeam(message.origin.team))
|
}
|
||||||
team->RemoveImage(message.image_deleted.info);
|
|
||||||
break;
|
break;
|
||||||
}
|
|
||||||
|
|
||||||
case B_DEBUGGER_MESSAGE_POST_SYSCALL:
|
case B_DEBUGGER_MESSAGE_POST_SYSCALL:
|
||||||
case B_DEBUGGER_MESSAGE_SIGNAL_RECEIVED:
|
case B_DEBUGGER_MESSAGE_SIGNAL_RECEIVED:
|
||||||
|
|||||||
Reference in New Issue
Block a user