/*
#
# CDDL HEADER START
#
# The contents of this file are subject to the terms of the
# Common Development and Distribution License (the "License").
# You may not use this file except in compliance with the License.
#
# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
# or http://www.opensolaris.org/os/licensing.
# See the License for the specific language governing permissions
# and limitations under the License.
#
# When distributing Covered Code, include this CDDL HEADER in each
# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
# If applicable, add the following below this CDDL HEADER, with the
# fields enclosed by brackets "[]" replaced with your own identifying
# information: Portions Copyright [yyyy] [name of copyright owner]
#
# CDDL HEADER END
#
*/
/*
#
# Copyright (c) 2010. Oracle and/or its affiliates. All rights reserved.
# Use is subject to license terms.
#
*/
#include "search.h"
#include "common.h"
#include "../config.h"
#define INDEX_LINES 23236
ResultSet *index_c = NULL;
int
initIndex() {
FILE *f;
char buf[500];
gchar* datafile = g_strdup_printf ("%s/CommandAssistantIndex", CMDASSIST_DATADIR);
f = fopen(datafile, "r");
g_free (datafile);
if( f == NULL) {
printf("open file failure\n");
return 1;
}
index_c = malloc(sizeof(ResultSet));
index_c->size = 0;
index_c->item = malloc(INDEX_LINES * sizeof(ItemSet));
int count = 0;
fgets(buf, sizeof(buf), f);
while (!feof(f) && count < INDEX_LINES) {
buf[strlen(buf)-1] = ' ';
const char *split = "\t";
char *p;
p = strtok(buf, split);
if(p != NULL){
strncpy(index_c->item[count].type, p, sizeof(index_c->item[count].type)-1);
index_c->item[count].type[sizeof(index_c->item[count].type) -1 ] = '\0';
p = strtok(NULL, split);
}
if(p != NULL){
strncpy(index_c->item[count].command, p, sizeof(index_c->item[count].command)-1);
index_c->item[count].command[sizeof(index_c->item[count].command)-1] = '\0';
p = strtok(NULL, split);
}
if(p !=NULL) {
strncpy(index_c->item[count].url, p, sizeof(index_c->item[count].url)-1);
index_c->item[count].url[sizeof(index_c->item[count].url)-1] = '\0';
p = strtok(NULL, split);
}
if(p != NULL){
strncpy(index_c->item[count].title, p, sizeof(index_c->item[count].title)-1);
index_c->item[count].title[sizeof(index_c->item[count].title)-1] = '\0';
p = strtok(NULL, split);
}
fgets(buf, sizeof(buf), f);
index_c->size++;
count++;
}
return 0;
}
static int
dosearch(char *str, ResultSet *rs, int max) {
if(index_c == NULL)
return 1;
int i;
for(i=0; i<INDEX_LINES; i++) {
if(rs->size >= max) {
return 0;
}
char *command = index_c->item[i].command;
char *p = strstr(command, str);
if(p && (p-command == 0)) {
//debug_printf("found: %s", command);
strcpy(rs->item[rs->size].command, index_c->item[i].command);
strcpy(rs->item[rs->size].title, index_c->item[i].title);
strcpy(rs->item[rs->size].url, index_c->item[i].url);
strcpy(rs->item[rs->size].type, index_c->item[i].type);
rs->size++;
}
}
return 0;
}
static int
toLowerCase(char *str) {
int i;
for(i = 0; str[i]; i++) {
str[i] = tolower(str[i]);
}
}
static int
titleSearch(char *word, ResultSet *rs, int max_size) {
if(index_c == NULL)
return 1;
char str[50];
strncpy(str, word, sizeof(str)-1);
str[sizeof(str)-1] = '\0';
toLowerCase(str);
int i;
for(i=0; i<INDEX_LINES; i++) {
if(rs->size >= max_size) {
return 0;
}
char title[50];
strncpy(title, index_c->item[i].title, sizeof(title)-1);
title[sizeof(title)-1] = '\0';
toLowerCase(title);
char *p = strstr(title, str);
if(p && (p - title == 0)) {
debug_printf("found: %s", title);
strcpy(rs->item[rs->size].command, index_c->item[i].command);
strcpy(rs->item[rs->size].title, index_c->item[i].title);
strcpy(rs->item[rs->size].url, index_c->item[i].url);
strcpy(rs->item[rs->size].type, index_c->item[i].type);
rs->size++;
}
}
return 0;
}
static int
dashSearch(char *word, ResultSet *rs, int max_size) {
int i= 0;
if(index_c == NULL)
return 1;
char command[20];
char cond[20];
char *pri = strchr(word, ' ');
if(pri != NULL) {
strncpy(command, word, pri - word);
command[pri - word] = '\0';
pri = strchr(pri, '-');
if(!pri)
return 1;
strncpy(cond, pri+1, sizeof(cond)-1);
cond[sizeof(cond)-1] = '\0';
} else {
return 1;
}
debug_printf("\n\nsize: %s\n\n", cond);
ResultSet set;
set.size = 0;
set.item = malloc(INDEX_LINES * sizeof(ItemSet));
dosearch(command, &set, INDEX_LINES);
for(i=0; i< set.size; i++) {
char *sCommand = set.item[i].command;
if(strstr(sCommand, cond)) {
if(rs->size >= max_size) {
break;
}
debug_printf("found: %s", sCommand);
strcpy(rs->item[rs->size].command, set.item[i].command);
strcpy(rs->item[rs->size].title, set.item[i].title);
strcpy(rs->item[rs->size].url, set.item[i].url);
strcpy(rs->item[rs->size].type, set.item[i].type);
rs->size++;
}
}
free(set.item);
return 0;
}
int doLocalSearch(char *str, cmdassist_config *conf, SearchResult *command, int max_size)
{
if(index_c == NULL) {
initIndex();
}
ResultSet rs;
rs.size = 0;
rs.item = malloc(max_size * sizeof(ItemSet));
dosearch(str, &rs, max_size);
int size = rs.size;
if(size == 0) {
dashSearch(str, &rs, max_size);
}
size = rs.size ;
if(size == 0) {
titleSearch(str, &rs, max_size);
}
size = rs.size ;
command->size = size;
command->list = malloc(size * sizeof(ResultItem));
int i;
for(i=0; i<size; i++) {
strncpy(command->list[i].type, rs.item[i].type, sizeof(command->list[i].type) -1);
command->list[i].type[sizeof(command->list[i].type) -1] = '\0';
strncpy(command->list[i].url, rs.item[i].url, sizeof(command->list[i].url)-1);
command->list[i].url[sizeof(command->list[i].url)-1] = '\0';
strncpy(command->list[i].command, rs.item[i].command, sizeof(command->list[i].command)-1);
command->list[i].command[sizeof(command->list[i].command)-1] = '\0';
strncpy(command->list[i].title, rs.item[i].title, sizeof(command->list[i].title)-1);
command->list[i].title[sizeof(command->list[i].title)-1] = '\0';
strncpy(command->list[i].score, "0", sizeof(command->list[i].score)-1);
strncpy(command->list[i].desc, "n/a", sizeof(command->list[i].desc)-1);
strncpy(command->list[i].size, "0", sizeof(command->list[i].size)-1);
}
if(rs.item != NULL) {
free(rs.item);
rs.item = NULL;
}
return 0;
}