1dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 2dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Copyright (C) 2007 The Android Open Source Project 3dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * 4dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License"); 5dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * you may not use this file except in compliance with the License. 6dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * You may obtain a copy of the License at 7dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * 8dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * http://www.apache.org/licenses/LICENSE-2.0 9dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * 10dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Unless required by applicable law or agreed to in writing, software 11dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS, 12dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * See the License for the specific language governing permissions and 14dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * limitations under the License. 15dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 16dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include "cutils/event_tag_map.h" 17dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include "cutils/log.h" 18dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 19dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <stdlib.h> 20dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <string.h> 21dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <fcntl.h> 22dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <sys/mman.h> 23dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <errno.h> 24dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#include <assert.h> 25dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 26dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project#define OUT_TAG "EventTagMap" 27dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 28dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 29dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Single entry. 30dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 31dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projecttypedef struct EventTag { 32dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project unsigned int tagIndex; 33dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project const char* tagStr; 34dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} EventTag; 35dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 36dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 37dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Map. 38dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 39dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstruct EventTagMap { 40dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* memory-mapped source file; we get strings from here */ 41dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project void* mapAddr; 42dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project size_t mapLen; 43dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 44dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* array of event tags, sorted numerically by tag index */ 45dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project EventTag* tagArray; 46dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project int numTags; 47dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project}; 48dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 49dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* fwd */ 50dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic int processFile(EventTagMap* map); 51dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic int countMapLines(const EventTagMap* map); 52dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic int parseMapLines(EventTagMap* map); 53dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic int scanTagLine(char** pData, EventTag* tag, int lineNum); 54dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic int sortTags(EventTagMap* map); 55dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic void dumpTags(const EventTagMap* map); 56dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 57dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 58dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 59dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Open the map file and allocate a structure to manage it. 60dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * 61dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * We create a private mapping because we want to terminate the log tag 62dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * strings with '\0'. 63dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 64dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source ProjectEventTagMap* android_openEventTagMap(const char* fileName) 65dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 66dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project EventTagMap* newTagMap; 67dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project off_t end; 68dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project int fd = -1; 69dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 70dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project newTagMap = calloc(1, sizeof(EventTagMap)); 71dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (newTagMap == NULL) 72dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return NULL; 73dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 74dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project fd = open(fileName, O_RDONLY); 75dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (fd < 0) { 76dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project fprintf(stderr, "%s: unable to open map '%s': %s\n", 77dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project OUT_TAG, fileName, strerror(errno)); 78dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project goto fail; 79dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 80dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 81dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project end = lseek(fd, 0L, SEEK_END); 82dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project (void) lseek(fd, 0L, SEEK_SET); 83dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (end < 0) { 84dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project fprintf(stderr, "%s: unable to seek map '%s'\n", OUT_TAG, fileName); 85dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project goto fail; 86dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 87dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 88dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project newTagMap->mapAddr = mmap(NULL, end, PROT_READ | PROT_WRITE, MAP_PRIVATE, 89dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project fd, 0); 90dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (newTagMap->mapAddr == MAP_FAILED) { 91dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project fprintf(stderr, "%s: mmap(%s) failed: %s\n", 92dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project OUT_TAG, fileName, strerror(errno)); 93dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project goto fail; 94dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 95dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project newTagMap->mapLen = end; 96dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 97dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (processFile(newTagMap) != 0) 98dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project goto fail; 99dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 100dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return newTagMap; 101dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 102dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectfail: 103dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project android_closeEventTagMap(newTagMap); 104dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (fd >= 0) 105dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project close(fd); 106dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return NULL; 107dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 108dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 109dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 110dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Close the map. 111dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 112dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectvoid android_closeEventTagMap(EventTagMap* map) 113dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 114dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (map == NULL) 115dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return; 116dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 117dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project munmap(map->mapAddr, map->mapLen); 118dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project free(map); 119dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 120dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 121dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 122dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Look up an entry in the map. 123dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * 124dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * The entries are sorted by tag number, so we can do a binary search. 125dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 126dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectconst char* android_lookupEventTag(const EventTagMap* map, int tag) 127dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 128dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project int hi, lo, mid; 129dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 130dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project lo = 0; 131dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project hi = map->numTags-1; 132dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 133dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project while (lo <= hi) { 134dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project int cmp; 135dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 136dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project mid = (lo+hi)/2; 137dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project cmp = map->tagArray[mid].tagIndex - tag; 138dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (cmp < 0) { 139dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* tag is bigger */ 140dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project lo = mid + 1; 141dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else if (cmp > 0) { 142dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* tag is smaller */ 143dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project hi = mid - 1; 144dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else { 145dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* found */ 146dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return map->tagArray[mid].tagStr; 147dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 148dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 149dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 150dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return NULL; 151dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 152dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 153dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 154dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 155dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 156dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Determine whether "c" is a whitespace char. 157dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 158dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic inline int isCharWhitespace(char c) 159dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 160dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return (c == ' ' || c == '\n' || c == '\r' || c == '\t'); 161dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 162dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 163dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 164dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Determine whether "c" is a valid tag char. 165dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 166dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic inline int isCharValidTag(char c) 167dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 168dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return ((c >= 'A' && c <= 'Z') || 169dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project (c >= 'a' && c <= 'z') || 170dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project (c >= '0' && c <= '9') || 171dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project (c == '_')); 172dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 173dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 174dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 175dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Determine whether "c" is a valid decimal digit. 176dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 177dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic inline int isCharDigit(char c) 178dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 179dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return (c >= '0' && c <= '9'); 180dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 181dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 182dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 183dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 184dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Crunch through the file, parsing the contents and creating a tag index. 185dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 186dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic int processFile(EventTagMap* map) 187dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 188dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project EventTag* tagArray = NULL; 189dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 190dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* get a tag count */ 191dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project map->numTags = countMapLines(map); 192dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (map->numTags < 0) 193dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return -1; 194dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 195dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project //printf("+++ found %d tags\n", map->numTags); 196dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 197dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* allocate storage for the tag index array */ 198dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project map->tagArray = calloc(1, sizeof(EventTag) * map->numTags); 199dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (map->tagArray == NULL) 200dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return -1; 201dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 202dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* parse the file, null-terminating tag strings */ 203dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (parseMapLines(map) != 0) { 204dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project fprintf(stderr, "%s: file parse failed\n", OUT_TAG); 205dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return -1; 206dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 207dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 208dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* sort the tags and check for duplicates */ 209dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (sortTags(map) != 0) 210dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return -1; 211dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 212dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return 0; 213dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 214dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 215dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 216dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Run through all lines in the file, determining whether they're blank, 217dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * comments, or possibly have a tag entry. 218dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * 219dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * This is a very "loose" scan. We don't try to detect syntax errors here. 220dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * The later pass is more careful, but the number of tags found there must 221dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * match the number of tags found here. 222dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * 223dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Returns the number of potential tag entries found. 224dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 225dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic int countMapLines(const EventTagMap* map) 226dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 227dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project int numTags, unknown; 228dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project const char* cp; 229dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project const char* endp; 230dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 231dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project cp = (const char*) map->mapAddr; 232dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project endp = cp + map->mapLen; 233dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 234dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project numTags = 0; 235dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project unknown = 1; 236dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project while (cp < endp) { 237dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (*cp == '\n') { 238dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project unknown = 1; 239dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else if (unknown) { 240dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (isCharDigit(*cp)) { 241dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* looks like a tag to me */ 242dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project numTags++; 243dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project unknown = 0; 244dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else if (isCharWhitespace(*cp)) { 245dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* might be leading whitespace before tag num, keep going */ 246dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else { 247dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* assume comment; second pass can complain in detail */ 248dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project unknown = 0; 249dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 250dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else { 251dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* we've made up our mind; just scan to end of line */ 252dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 253dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project cp++; 254dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 255dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 256dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return numTags; 257dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 258dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 259dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 260dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Parse the tags out of the file. 261dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 262dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic int parseMapLines(EventTagMap* map) 263dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 264dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project int tagNum, lineStart, lineNum; 265dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project char* cp; 266dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project char* endp; 267dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 268dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project cp = (char*) map->mapAddr; 269dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project endp = cp + map->mapLen; 270dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 271dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* insist on EOL at EOF; simplifies parsing and null-termination */ 272dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (*(endp-1) != '\n') { 273dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project fprintf(stderr, "%s: map file missing EOL on last line\n", OUT_TAG); 274dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return -1; 275dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 276dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 277dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project tagNum = 0; 278dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project lineStart = 1; 279dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project lineNum = 1; 280dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project while (cp < endp) { 281dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project //printf("{%02x}", *cp); fflush(stdout); 282dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (*cp == '\n') { 283dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project lineStart = 1; 284dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project lineNum++; 285dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else if (lineStart) { 286dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (*cp == '#') { 287dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* comment; just scan to end */ 288dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project lineStart = 0; 289dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else if (isCharDigit(*cp)) { 290dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* looks like a tag; scan it out */ 291dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (tagNum >= map->numTags) { 292dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project fprintf(stderr, 293dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project "%s: more tags than expected (%d)\n", OUT_TAG, tagNum); 294dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return -1; 295dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 296dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (scanTagLine(&cp, &map->tagArray[tagNum], lineNum) != 0) 297dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return -1; 298dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project tagNum++; 299dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project lineNum++; // we eat the '\n' 300dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* leave lineStart==1 */ 301dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else if (isCharWhitespace(*cp)) { 302dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* looks like leading whitespace; keep scanning */ 303dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else { 304dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project fprintf(stderr, 305dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project "%s: unexpected chars (0x%02x) in tag number on line %d\n", 306dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project OUT_TAG, *cp, lineNum); 307dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return -1; 308dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 309dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else { 310dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* this is a blank or comment line */ 311dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 312dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project cp++; 313dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 314dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 315dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (tagNum != map->numTags) { 316dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project fprintf(stderr, "%s: parsed %d tags, expected %d\n", 317dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project OUT_TAG, tagNum, map->numTags); 318dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return -1; 319dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 320dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 321dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return 0; 322dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 323dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 324dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 325dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Scan one tag line. 326dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * 327dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * "*pData" should be pointing to the first digit in the tag number. On 328dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * successful return, it will be pointing to the last character in the 329dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * tag line (i.e. the character before the start of the next line). 330dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * 331dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Returns 0 on success, nonzero on failure. 332dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 333dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic int scanTagLine(char** pData, EventTag* tag, int lineNum) 334dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 335dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project char* cp = *pData; 336dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project char* startp; 337dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project char* endp; 338dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project unsigned long val; 339dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 340dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project startp = cp; 341dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project while (isCharDigit(*++cp)) 342dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project ; 343dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project *cp = '\0'; 344dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 345dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project val = strtoul(startp, &endp, 10); 346dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project assert(endp == cp); 347dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (endp != cp) 348dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project fprintf(stderr, "ARRRRGH\n"); 349dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 350dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project tag->tagIndex = val; 351dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 352dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project while (*++cp != '\n' && isCharWhitespace(*cp)) 353dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project ; 354dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 355dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (*cp == '\n') { 356dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project fprintf(stderr, 357dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project "%s: missing tag string on line %d\n", OUT_TAG, lineNum); 358dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return -1; 359dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 360dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 361dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project tag->tagStr = cp; 362dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 363dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project while (isCharValidTag(*++cp)) 364dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project ; 365dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 366dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (*cp == '\n') { 367dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* null terminate and return */ 368dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project *cp = '\0'; 369dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else if (isCharWhitespace(*cp)) { 370dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* CRLF or trailin spaces; zap this char, then scan for the '\n' */ 371dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project *cp = '\0'; 372dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 373dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project /* just ignore the rest of the line till \n 374dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project TODO: read the tag description that follows the tag name 375dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 376dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project while (*++cp != '\n') { 377dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 378dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } else { 379dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project fprintf(stderr, 380dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project "%s: invalid tag chars on line %d\n", OUT_TAG, lineNum); 381dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return -1; 382dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 383dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 384dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project *pData = cp; 385dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 386dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project //printf("+++ Line %d: got %d '%s'\n", lineNum, tag->tagIndex, tag->tagStr); 387dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return 0; 388dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 389dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 390dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 391dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Compare two EventTags. 392dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 393dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic int compareEventTags(const void* v1, const void* v2) 394dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 395dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project const EventTag* tag1 = (const EventTag*) v1; 396dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project const EventTag* tag2 = (const EventTag*) v2; 397dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 398dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return tag1->tagIndex - tag2->tagIndex; 399dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 400dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 401dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 402dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Sort the EventTag array so we can do fast lookups by tag index. After 403dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * the sort we do a quick check for duplicate tag indices. 404dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * 405dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Returns 0 on success. 406dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 407dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic int sortTags(EventTagMap* map) 408dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 409dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project int i; 410dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 411dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project qsort(map->tagArray, map->numTags, sizeof(EventTag), compareEventTags); 412dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 413dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project for (i = 1; i < map->numTags; i++) { 414dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project if (map->tagArray[i].tagIndex == map->tagArray[i-1].tagIndex) { 415dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project fprintf(stderr, "%s: duplicate tag entries (%d:%s and %d:%s)\n", 416dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project OUT_TAG, 417dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project map->tagArray[i].tagIndex, map->tagArray[i].tagStr, 418dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project map->tagArray[i-1].tagIndex, map->tagArray[i-1].tagStr); 419dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return -1; 420dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 421dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 422dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 423dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project return 0; 424dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 425dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 426dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project/* 427dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project * Dump the tag array for debugging. 428dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project */ 429dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Projectstatic void dumpTags(const EventTagMap* map) 430dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project{ 431dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project int i; 432dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 433dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project for (i = 0; i < map->numTags; i++) { 434dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project const EventTag* tag = &map->tagArray[i]; 435dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project printf(" %3d: %6d '%s'\n", i, tag->tagIndex, tag->tagStr); 436dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project } 437dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project} 438dd7bc3319deb2b77c5d07a51b7d6cd7e11b5beb0The Android Open Source Project 439