Search
lxdream.org :: lxdream/src/watch.c
lxdream 0.9.1
released Jun 29
Download Now
filename src/watch.c
changeset 736:a02d1475ccfd
prev561:533f6b478071
author nkeynes
date Wed Nov 05 10:05:08 2008 +0000 (15 years ago)
permissions -rw-r--r--
last change Fix (extremely boneheaded) failure to convert pc to physical address before
storing in the translation cache (in other words, the translation cache was
effectively disabled for MMU code). MMU code is now about 3 times faster...
view annotate diff log raw
     1 /**
     2  * $Id$
     3  *
     4  * Watchpoint support (for debugging)
     5  *
     6  * Copyright (c) 2005 Nathan Keynes.
     7  *
     8  * This program is free software; you can redistribute it and/or modify
     9  * it under the terms of the GNU General Public License as published by
    10  * the Free Software Foundation; either version 2 of the License, or
    11  * (at your option) any later version.
    12  *
    13  * This program is distributed in the hope that it will be useful,
    14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
    15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    16  * GNU General Public License for more details.
    17  */
    19 #include <stdlib.h>
    20 #include <string.h>
    21 #include "mem.h"
    23 struct watch_point {
    24     uint32_t start;
    25     uint32_t end;
    26     int flags;
    27 };
    29 struct watch_point *watch_arr = NULL;
    30 int watch_count = 0, watch_capacity = 0;
    33 watch_point_t mem_new_watch( uint32_t start, uint32_t end, int flags )
    34 {
    35     int num;
    36     if( watch_arr == NULL ) {
    37         watch_capacity = 10;
    38         watch_arr = calloc( sizeof(struct watch_point), watch_capacity );
    39         num = 0;
    40     } else if( watch_count == watch_capacity ) {
    41         struct watch_point *tmp = realloc( watch_arr, sizeof(struct watch_point) * watch_capacity * 2 );
    42         if( tmp == NULL )
    43             return NULL;
    44         watch_arr = tmp;
    45         memset( &watch_arr[watch_capacity], 0, sizeof( struct watch_point ) * watch_capacity );
    46         num = watch_capacity;
    47         watch_capacity *= 2;
    48     } else {
    49         for( num=0; num<watch_capacity; num++ ) {
    50             if( watch_arr[num].flags == 0 )
    51                 break;
    52         }
    53     }
    54     watch_arr[num].start = start & 0x1FFFFFFF;
    55     watch_arr[num].end = end & 0x1FFFFFFF;
    56     watch_arr[num].flags = flags;
    57     watch_count++;
    58     return &watch_arr[num];
    59 }
    61 void mem_delete_watch( watch_point_t watch )
    62 {
    63     if( watch_arr == NULL )
    64         return;
    65     int num = watch - watch_arr;
    66     if( num < 0 || num >= watch_capacity )
    67         return;
    68     watch->start = watch->end = 0;
    69     watch->flags = 0;
    70     watch_count--;
    71 }
    74 watch_point_t mem_is_watched( uint32_t addr, int size, int op )
    75 {
    76     int i, count;
    77     addr &= 0x1FFFFFFF;
    78     for( i=0, count=0; count< watch_count; i++ ) {
    79         if( watch_arr[i].flags == 0 )
    80             continue;
    81         count++;
    82         if( watch_arr[i].flags & op &&
    83                 watch_arr[i].start < addr+size &&
    84                 watch_arr[i].end >= addr ) {
    85             return &watch_arr[i];
    86         }
    87     }
    88     return NULL;
    89 }
.