示例#1
0
static int goal_enter(void)
{
    const char *s1 = _("New Record");
    const char *s2 = _("GOAL");

    int id, jd, kd, ld, md;

    const struct level *l = get_level(curr_level());

    int high = progress_lvl_high();

    if (new_name)
    {
        progress_rename(0);
        new_name = 0;
    }

    if ((id = gui_vstack(0)))
    {
        int gid;

        if (high)
            gid = gui_label(id, s1, GUI_MED, GUI_ALL, gui_grn, gui_grn);
        else
            gid = gui_label(id, s2, GUI_LRG, GUI_ALL, gui_blu, gui_grn);

        gui_space(id);

        if (curr_mode() == MODE_CHALLENGE)
        {
            int coins, score, balls;
            char msg[MAXSTR] = "";
            int i;

            /* Reverse-engineer initial score and balls. */

            if (resume)
            {
                coins = 0;
                score = curr_score();
                balls = curr_balls();
            }
            else
            {
                coins = curr_coins();
                score = curr_score() - coins;
                balls = curr_balls();

                for (i = curr_score(); i > score; i--)
                    if (progress_reward_ball(i))
                        balls--;
            }

            sprintf(msg, ngettext("%d new bonus level",
                                  "%d new bonus levels",
                                  curr_bonus()), curr_bonus());

            if ((jd = gui_hstack(id)))
            {
                gui_filler(jd);

                if ((kd = gui_vstack(jd)))
                {
                    if ((ld = gui_hstack(kd)))
                    {
                        if ((md = gui_harray(ld)))
                        {
                            balls_id = gui_count(md, 100, GUI_MED, GUI_NE);
                            gui_label(md, _("Balls"), GUI_SML, 0,
                                      gui_wht, gui_wht);
                        }
                        if ((md = gui_harray(ld)))
                        {
                            score_id = gui_count(md, 1000, GUI_MED, 0);
                            gui_label(md, _("Score"), GUI_SML, 0,
                                      gui_wht, gui_wht);
                        }
                        if ((md = gui_harray(ld)))
                        {
                            coins_id = gui_count(md, 100, GUI_MED, 0);
                            gui_label(md, _("Coins"), GUI_SML, GUI_NW,
                                      gui_wht, gui_wht);
                        }

                        gui_set_count(balls_id, balls);
                        gui_set_count(score_id, score);
                        gui_set_count(coins_id, coins);
                    }

                    gui_label(kd, msg, GUI_SML, GUI_BOT, 0, 0);
                }

                gui_filler(jd);
            }

            gui_space(id);
        }
        else
        {
            balls_id = score_id = coins_id = 0;
        }

        gui_score_board(id, (GUI_MOST_COINS |
                             GUI_BEST_TIMES |
                             GUI_FAST_UNLOCK), 1, high);

        gui_space(id);

        if ((jd = gui_harray(id)))
        {
            if      (progress_done())
                gui_start(jd, _("Finish"), GUI_SML, GOAL_DONE, 0);
            else if (progress_last())
                gui_start(jd, _("Finish"), GUI_SML, GOAL_LAST, 0);

            if (progress_next_avail())
                gui_start(jd, _("Next Level"),  GUI_SML, GOAL_NEXT, 0);

            if (progress_same_avail())
                gui_start(jd, _("Retry Level"), GUI_SML, GOAL_SAME, 0);

            if (demo_saved())
                gui_state(jd, _("Save Replay"), GUI_SML, GOAL_SAVE, 0);
        }

        if (!resume)
            gui_pulse(gid, 1.2f);

        gui_layout(id, 0, 0);

    }

    set_score_board(&l->score.most_coins,  progress_coin_rank(),
                    &l->score.best_times,  progress_time_rank(),
                    &l->score.fast_unlock, progress_goal_rank());

    audio_music_fade_out(2.0f);

    video_clr_grab();

    /* Reset hack. */
    resume = 0;

    return id;
}
void
GameSession::restart_level()
{
  game_pause   = false;
  exit_status  = ES_NONE;
  end_sequence = NO_ENDSEQUENCE;

  fps_timer.init(true);
  frame_timer.init(true);

  float old_x_pos = -1;

  if (world)
    { // Tux has lost a life, so we try to respawn him at the nearest reset point
      old_x_pos = world->get_tux()->base.x;
    }
  
  delete world;

  if (st_gl_mode == ST_GL_LOAD_LEVEL_FILE)
    {
      world = new World(subset);
    }
  else if (st_gl_mode == ST_GL_DEMO_GAME)
    {
      world = new World(subset);
    }
  else
    {
      world = new World(subset, levelnb);
    }

  // Set Tux to the nearest reset point
  if (old_x_pos != -1)
    {
      ResetPoint best_reset_point = { -1, -1 };
      for(std::vector<ResetPoint>::iterator i = get_level()->reset_points.begin();
          i != get_level()->reset_points.end(); ++i)
        {
          if (i->x - screen->w/2 < old_x_pos && best_reset_point.x < i->x)
            best_reset_point = *i;
        }
      
      if (best_reset_point.x != -1)
        {
          world->get_tux()->base.x = best_reset_point.x;
          world->get_tux()->base.y = best_reset_point.y;
          world->get_tux()->old_base = world->get_tux()->base;
          world->get_tux()->previous_base = world->get_tux()->base;

          if(collision_object_map(world->get_tux()->base)) {
              std::cout << "Warning: reset point inside a wall.\n";
          }                                                                  

          scroll_x = best_reset_point.x - screen->w/2;
        }
    }
    
  if (st_gl_mode != ST_GL_DEMO_GAME)
    {
      if(st_gl_mode == ST_GL_PLAY || st_gl_mode == ST_GL_LOAD_LEVEL_FILE)
        levelintro();
    }

  time_left.init(true);
  start_timers();
  world->play_music(LEVEL_MUSIC);
}
示例#3
0
void LevelGraphic::draw()
{
	if (nivel_activo()) {
		al_draw_bitmap(bmp,0,0,0);

		switch (get_estado())
		{
			case INICIALIZADO:
				if (font_transito)
				{
					al_draw_textf(font_transito,al_map_rgb(8,8,138),300 ,270 ,ALLEGRO_ALIGN_CENTRE , "%s: %d","nivel", get_level());
				} else
				{
					printf("error al cargar el font\n");
				}
				break;
			case CREADO:
				if (font)
				{
					al_draw_textf(font,al_map_rgb(8,8,138),get_x() ,get_y() ,ALLEGRO_ALIGN_LEFT , "%s: %d",title.c_str(), get_level());
				} else
				{
					printf("error al cargar el font\n");
				}
				break;
			case DESTRUIDO:
				if (last_level()){
					if (font_transito)
					{
						al_draw_textf(font_transito,al_map_rgb(8,8,138),300 ,270 ,ALLEGRO_ALIGN_CENTRE , "%s","Game over");
					} else
					{
						printf("error al cargar el font\n");
					}
				} else {
					if (font_transito)
					{
						al_draw_textf(font_transito,al_map_rgb(8,8,138),300 ,270 ,ALLEGRO_ALIGN_CENTRE , "%s","Sigue jugando");
					} else
					{
						printf("error al cargar el font\n");
					}
				}
				break;
			default:
				break;

		}

	}
		//	al_draw_text(font, al_map_rgb(255, 0, 255), 50, 50, 0, "Hello World");
}
示例#4
0
void* buddy_exact_alloc(void** ptr, size_t size) {

    d_printf("Internal fragmentation detected : \n");
    void* actual_pointer = *ptr;

    item* current_block_item = (item*)actual_pointer;
    item* new_current_block_item;
    
    int current_size = current_block_item->size;
    int current_level = get_level(current_size);
    int previous_power_of_two_level, block_size, level;
      
    d_printf("current_level : %d\n", current_level);
    d_printf("current_size : %d\n", current_size);
    
    int extra_allocated = (1UL << current_level) - size;
    d_printf("Extra space allocated : %d\n", extra_allocated);

    while(extra_allocated) {

        if(extra_allocated == get_next_power_of_2(extra_allocated)) {

            level = get_level(extra_allocated);
            block_size = 1UL << level;
            new_current_block_item = (current_block_item + (1UL << level));
            new_current_block_item->size = current_block_item->size - block_size;
            current_block_item->size = block_size;

            /* Check if there is already free block of that level */
            /* If no, make this the first one */

            d_printf("Adding %p of size %ld back to the freelist level : %d\n", current_block_item, current_block_item->size, level);
            if(freelist_object->freelist[level] == NULL)
                freelist_object->freelist[level] = (void*)current_block_item;

            /* Else get the first one, link it to this block and make the block the first in that level */
            else {
                current_block_item->next = (item*)freelist_object->freelist[level];
                freelist_object->freelist[level] = (void*)current_block_item;
            }
            new_current_block_item->in_use = true;
            return (void*)new_current_block_item;        
        }

        /*d_printf("Next power of 2 of extra allocated : %d\n", get_next_power_of_2(extra_allocated));
        d_printf("Next power of 2's level of extra allocated : %d\n", get_level(get_next_power_of_2(extra_allocated)));*/
        previous_power_of_two_level = get_level(get_next_power_of_2(extra_allocated));
        --previous_power_of_two_level;
        // d_printf("previous_power_of_two_level: %d\n", previous_power_of_two_level);
        block_size = 1UL << previous_power_of_two_level;

        new_current_block_item = current_block_item + block_size;
        new_current_block_item->size = current_block_item->size - block_size;
        current_block_item->size = block_size;

        /* Check if there is already free block of that level */
        /* If no, make this the first one */
        d_printf("Adding %p of size %ld back to the freelist level : %d\n", current_block_item, current_block_item->size, previous_power_of_two_level);
        if(freelist_object->freelist[previous_power_of_two_level] == NULL)
            freelist_object->freelist[previous_power_of_two_level] = (void*)current_block_item;

        /* Else get the first one, link it to this block and make the block the first in that level */
        else {
            current_block_item->next = (item*)freelist_object->freelist[previous_power_of_two_level];
            freelist_object->freelist[previous_power_of_two_level] = (void*)current_block_item;
        }

        current_block_item = new_current_block_item;
        extra_allocated -= block_size;
        // d_printf("extra_allocated : %d\n", extra_allocated);
    }

    return actual_pointer; // The control won't reach here
}
示例#5
0
void* buddy_alloc(size_t size) {
    
    void* allocated_block = NULL;                  // The object to return
    void* allocated_block_from_merge = NULL;
    item* allocated_block_item = NULL;
    void* available_block = NULL; 
    item* available_block_item = NULL;
    int next_power_of_2 = 0;
    int calculated_level = 0;
    int j = 0;
    void *list = NULL;
    item *new_head;

    printf("Allocation request for %d\n", (int)size);

    //Calculate the power of 2 big enough to hold 'size'
    next_power_of_2 = get_next_power_of_2(size);
    calculated_level = get_level(next_power_of_2);

    d_printf("next_power_of_2 %d\n", next_power_of_2);
    d_printf("calculated_level %d\n", calculated_level);

    assert(calculated_level < freelist_object->max_level);

    // Check the free-list if there are any free blocks for that level in the freelist array
    // If not, find a block in the upper level.
    // Split the block
    // Assign the block to the return object.

    for (j = calculated_level; j <= freelist_object->max_level; j++) {

        list = freelist_object->freelist[j];
        if (list == NULL)
            continue;

        available_block_item = (item *)list;

        /* Detach it from it's current position in the free list array */
        new_head = available_block_item->next;

        if(new_head == NULL)
            freelist_object->freelist[j] = NULL;
        else
            freelist_object->freelist[j] = (void*)new_head;

        if(available_block_item == NULL) {

            printf("Memory full. Try evicting");
            return NULL;
        }

        d_printf("Big enough block %p found at level %d\n", available_block_item, j);

        /* Trim if a higher order block than necessary was allocated */
        allocated_block_item = available_block_item;

        while (j > calculated_level) {

            /* Perform the splitting iteratively */
            // , (int)(((item *)allocated_block)->size)
            // d_printf("Size : %ld\n", allocated_block_item->size);
            d_printf("Splitting %p at level %d ", available_block_item, j);
            --j;
            
            available_block_item = available_block_item + (1UL << j);
            available_block_item->size = (1UL << j);
            allocated_block_item->size = (1UL << j);
            d_printf("into %p and %p\n", allocated_block_item, available_block_item);

            /* Check if there is already free block of that level */
            /* If no, make this the first one */
            if(freelist_object->freelist[j] == NULL)
                freelist_object->freelist[j] = (void*)allocated_block_item;

            /* Else get the first one, link it to this block and make the block the first in that level */
            else {
                available_block_item->next = (item*)freelist_object->freelist[j];
                freelist_object->freelist[j] = (void*)allocated_block_item;
            }
            allocated_block_item = available_block_item;
        }

        d_printf("Block %p alloted out of the level %d\n", allocated_block_item, j);

        // Return the object if it does not cause internal fragmentatation
        if((1UL << calculated_level) - size == 0)
        {
            d_printf("No internal fragmentatation involved with this request size\n");
            allocated_block_item->in_use = true;
            allocated_block = (void*)allocated_block_item;
            return allocated_block;
        }

        //else invoke the buddy_exact_alloc method
        allocated_block = (void*)allocated_block_item;
        return buddy_exact_alloc(&allocated_block, size);
    }

    printf("No blocks found in higher levels of the free list. Exploring the lower levels and checking if something can be merged\n");
    available_block = (void*)available_block_item;
    allocated_block_from_merge = buddy_merge(size);
    if(allocated_block_from_merge == NULL) {
        printf("Memory full. Try evicting");
        return NULL;
    }
    d_printf("Block %p alloted out of the level %d\n", (item *)allocated_block_from_merge, get_level(((item *)allocated_block_from_merge)->size));
    return allocated_block_from_merge;
}
示例#6
0
int main(){
	Ty_Node *root= NULL;
	Ty_Node *p = NULL;
	char fpath[100];
	char order[100];
	element data;
	char a[100];
	char *token = NULL;
	char *token1 = NULL;
	char *separator = " ,\n";
	int level = 0;
	printf("파일 이름이 뭐인가요?\n");								
	scanf("%s", &fpath);													// 파일이름 입력


	fp = fopen(fpath, "r");	
	if(fp){																	// 파일이름이 존재할 때

		insert_from_file(&root);											// 파일로부터 노드 삽입
		while(1){
			printf("명령어를 입력하세요\n");
			fflush(stdin);													// scanf 버퍼 비우기
			scanf("%[^\n]s", &order);										// scanf 를 마치 gets 처럼 공백 무시하고 \n 까지 읽어들이는 방법
			token = strtok(order, separator);								// token 을 이용해 단어 분할
			switch(token[0]){												// 첫번째 명령어 부분을 switch 에 넣어 사용 case는 아스키코드값으로 

			case 105 :	// i
				token = strtok(NULL, separator);
				strcpy(data.name, token); 
				token = strtok(NULL, separator);
				data.key = atoi(token);
				insert_anode(&root, data);									// 추가정보를 data에 넣어서 노드에 삽입
				break;
			case 112 : 
				// p
				inorder(root);												// 중위순회방식으로 출력
				break;
			case 100 :  // d
				token = strtok(NULL, separator);
				delete_anode(root, token);									// 삭제
				break;
			case 115 :  // s
				token = strtok(NULL, separator);
				p = search_anode(root, token);								// 해당 키값의 노드정보 출력
				if(p !=NULL)
					printf("%s %d\n", p->data.name, p->data.key); 
				else
					printf("%s을 찾을 수 없습니다\n", token);
				break;
			case 118 :  // v
				token = strtok(NULL, separator);
				level = get_level(root, token);								// 해당 키값의 노드 높이 출력
				if(level !=0)
					printf("%s의 높이 : %d\n", token, level);
				else
					printf("%s을 찾을 수 없습니다\n", token);

				break;
			case 98 :  // b
				token = strtok(NULL, separator);
				get_sibling(root, token);									// 해당 키값의 노드 형제 출력
				break;
			case 104 : // h
				level = get_height(root);									// 높이 출력
				if(level !=NULL)
					printf("높이 : %d\n", level);
				break;
			case 101 : exit(0);												// 종료


			}
		}
	}
	else
	{
		printf("file 이름을 찾을 수 없습니다\n");
	}
}
示例#7
0
void* buddy_merge(size_t size_requested)
{
    //first determine from which level you can merge.
    item *level_iterator = NULL, *freelist_first_block = NULL, *new_block_to_be_formed = NULL;
    int level_found = 0;
    unsigned int total_block_size_in_a_level;
    size_t requested_size = size_requested;
    unsigned long previous_level = 0;
    previous_level = get_level(get_next_power_of_2(requested_size));    
    --previous_level;
    while(previous_level)
    {
        level_iterator = freelist_object->freelist[previous_level];
        while(level_iterator != NULL)
        {
            total_block_size_in_a_level = total_block_size_in_a_level + level_iterator->size;
            level_iterator = level_iterator->next;
        }
        if (total_block_size_in_a_level >= requested_size)
        {
            //we have found the level from where we have to merge.
            level_found = 1;
            break;
        }
        //continue looking.
        previous_level--;
    }
    if (level_found)
    {
        //we found the level. Now merge them and return the address.
        freelist_first_block = freelist_object->freelist[previous_level];
        level_iterator = freelist_object->freelist[previous_level];
        new_block_to_be_formed = level_iterator;
        while(requested_size )
        {
            //Assumption: Addresses are in increasing order
            //if not in use, then merge.
            if (!requested_size)
                break;
            new_block_to_be_formed->size += level_iterator->size;
            requested_size = requested_size - level_iterator->size;
            level_iterator = level_iterator->next;
        }
        level_iterator = level_iterator->next;
        new_block_to_be_formed->in_use = true;
        if (level_iterator != NULL)
        {
            freelist_object->freelist[previous_level] = level_iterator;
        }
        else
        {
            freelist_object->freelist[previous_level] = NULL;
        }
        return ((void*)new_block_to_be_formed);
    }
    else 
    {
        //sorry could not find smaller blocks to merge. Need to evict now.
        return NULL;
    }
}
示例#8
0
文件: draw.c 项目: jys673/Synergy
draw_pic(char filename1[30])
{
    int width,height;
    unsigned char c1,c2,c3,c4;
    int     ix, iy, i, j, inten, status, ip;
    double   x, y, tnew[2], told[2], retval, sigma[2], temp;
    double   rate, t0, t1, time;
    FILE *fd;
    char host[128];
    unsigned char r,g,b;
    int c;
    int screen;
    int ops;
    double flops;
    char filename[80];
    init_color();

    
     fd=fopen(filename1,"r");
     if (!fd) 
     fd=fopen("povray.out","r");
     if (!fd) { printf("\n file open error!"); exit(1); }
     c1=fgetc(fd); c2=fgetc(fd);
     c3=fgetc(fd); c4=fgetc(fd); 
     
     WIDTH=width=c1*256+c2; 
     HEIGHT=height=c3*256+c4;
     fflush(stdout);

/**  Image mapping ***/

    screen=DefaultScreen( mydisplay );
    depth=DefaultDepth(mydisplay, screen);
    if (depth==1)
    {
    format=XYPixmap;
    bitmap_pad=32;
    }
    else 
    {
     format=ZPixmap;
     bitmap_pad=8;
     if (depth>8) bitmap_pad=32;
    }
     image=XCreateImage(mydisplay, DefaultVisual(mydisplay,screen),
                        depth, format, 0, 0,
                        width, height, bitmap_pad,0);

     if (image==0)
      { printf("\n IMAGE structure allocate error!");
      }
     else
     {
      image->data=malloc(image->bytes_per_line * height);
      if (image->data ==0)
      printf("\n IMAGE memory allocate error!");
     }
     


/* ---- get image ----^^^^ */

                        for(i=1;i<=height;i++)
                       { 
                        int LINE_Y;
                        c1=fgetc(fd);
                        c2=fgetc(fd);
                        LINE_Y=c1*256+c2;
                        for(j=1;j<=width;j++)
                        {
                        int cc;
                        r=fgetc(fd); 
                        g=fgetc(fd);  
                        b=fgetc(fd);   
                        r=get_level(r);
                        g=get_level(g);
                        b=get_level(b);
                        cc=r*6*6+g*6+b;
                        c=scren[j][i]=cc;
			XSetForeground( mydisplay,
                                        mygc, C[c].pixel);
			XDrawPoint( mydisplay, 
                                    mywindow,
                                    mygc, j,LINE_Y );
                        XPutPixel(image,j,LINE_Y, C[c].pixel);
                         }
                       }

    	XFlush( mydisplay );
        XPutImage(mydisplay,mywindow,mygc,image,
                  1,1,1,1,width,height);
}
示例#9
0
文件: boots.c 项目: Lopo/Lotos
/*** Parse init section ***/
void parse_init_section(void) {
	static int in_section=0;
	int op,val,tmp;
	char *options[]={ 
		"mainport","wizport","linkport","system_logging","minlogin_level","mesg_life",
		"wizport_level","prompt_def","gatecrash_level","min_private","ignore_mp_level",
		"rem_user_maxlevel","rem_user_deflevel","verification","mesg_check_time",
		"max_users","heartbeat","login_idle_time","user_idle_time","password_echo",
		"ignore_sigterm","auto_connect","max_clones","ban_swearing","crash_action",
		"colour_def","time_out_afks","charecho_def","time_out_maxlevel","auto_purge",
		"auto_promote","personal_rooms","random_motds","startup_room_parse",
		"resolve_ip","flood_protect", "pueblo_enh", "auto_save", "susers_restrict",
		"auto_afk", "use_hosts_file", "*"
		};

if (!strcmp(wrd[0],"INIT:")) { 
  if (++in_section>1) {
    fprintf(stderr,"Lotos: Unexpected INIT section header on line %d.\n",config_line);
    boot_exit(1);
    }
  return;
  }
op=0; tmp=0;
while(strcmp(options[op],wrd[0])) {
  if (options[op][0]=='*') {
    fprintf(stderr,"Lotos: Unknown INIT option on line %d.\n",config_line);
    boot_exit(1);
    }
  ++op;
  }
if (!wrd[1][0]) {
  fprintf(stderr,"Lotos: Required parameter missing on line %d.\n",config_line);
  boot_exit(1);
  }
if (wrd[2][0] && wrd[2][0]!='#') {
  fprintf(stderr,"Lotos: Unexpected word following init parameter on line %d.\n",config_line);
  boot_exit(1);
  }
val=atoi(wrd[1]);
switch (op) {
  case 0: /* main port */
  case 1: /* wiz */
#ifdef NETLINKS
  case 2: /* link */
#endif
    if ((port[op]=val)<1 || val>65535) {
      fprintf(stderr,"Lotos: Illegal port number on line %d.\n",config_line);
      boot_exit(1);
      }
    return;
  
  case 3:  
    if ((tmp=onoff_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: System_logging must be ON or OFF on line %d.\n",config_line);
      boot_exit(1);
      }
    /* set the bits correctly */
    if (tmp) {
      amsys->logging=BIT_SET(amsys->logging,SYSLOG);
      amsys->logging=BIT_SET(amsys->logging,REQLOG);
#ifdef NETLINKS
      amsys->logging=BIT_SET(amsys->logging,NETLOG);
#endif
#ifdef DEBUG
      amsys->logging=BIT_SET(amsys->logging,DEBLOG);
#endif
      amsys->logging=BIT_SET(amsys->logging,ERRLOG);
      }
    else amsys->logging=0;
    return;
  
  case 4:
    if ((amsys->minlogin_level=get_level(wrd[1]))==-1) {
      if (strcmp(wrd[1],"NONE")) {
	fprintf(stderr,"Lotos: Unknown level specifier for minlogin_level on line %d.\n",config_line);
	boot_exit(1);	
        }
      amsys->minlogin_level=-1;
      }
    return;
    
  case 5:  /* message lifetime */
    if ((amsys->mesg_life=val)<1) {
      fprintf(stderr,"Lotos: Illegal message lifetime on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 6: /* wizport_level */
    if ((amsys->wizport_level=get_level(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Unknown level specifier for wizport_level on line %d.\n",config_line);
      boot_exit(1);	
      }
    return;

  case 7: /* prompt defaults */
    if ((amsys->prompt_def=onoff_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Prompt_def must be ON or OFF on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 8: /* gatecrash level */
    if ((amsys->gatecrash_level=get_level(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Unknown level specifier for gatecrash_level on line %d.\n",config_line);
      boot_exit(1);	
      }
    return;

  case 9:
    if (val<1) {
      fprintf(stderr,"Lotos: Number too low for min_private_users on line %d.\n",config_line);
      boot_exit(1);
      }
    amsys->min_private_users=val;
    return;

  case 10:
    if ((amsys->ignore_mp_level=get_level(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Unknown level specifier for ignore_mp_level on line %d.\n",config_line);
      boot_exit(1);	
      }
    return;

  case 11: 
    /* Max level a remote user can remotely log in if he doesn't have a local
       account. ie if level set to WIZ a GOD can only be a WIZ if logging in 
       from another server unless he has a local account of level GOD */
    if ((amsys->rem_user_maxlevel=get_level(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Unknown level specifier for rem_user_maxlevel on line %d.\n",config_line);
      boot_exit(1);	
      }
    return;

  case 12:
    /* Default level of remote user who does not have an account on site and
       connection is from a server of version 3.3.0 or lower. */
    if ((amsys->rem_user_deflevel=get_level(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Unknown level specifier for rem_user_deflevel on line %d.\n",config_line);
      boot_exit(1);	
      }
    return;

  case 13:
#ifdef NETLINKS
    if (strlen(wrd[1])>VERIFY_LEN) {
      fprintf(stderr,"Lotos: Verification too long on line %d.\n",config_line);
      boot_exit(1);	
      }
    strcpy(verification,wrd[1]);
#endif
    return;

  case 14: /* mesg_check_time */
    if (wrd[1][2]!=':'
	|| strlen(wrd[1])>5
	|| !isdigit(wrd[1][0]) 
	|| !isdigit(wrd[1][1])
	|| !isdigit(wrd[1][3]) 
	|| !isdigit(wrd[1][4])) {
      fprintf(stderr,"Lotos: Invalid message check time on line %d.\n",config_line);
      boot_exit(1);
      }
    sscanf(wrd[1],"%d:%d",&amsys->mesg_check_hour,&amsys->mesg_check_min);
    if (amsys->mesg_check_hour>23 || amsys->mesg_check_min>59) {
      fprintf(stderr,"Lotos: Invalid message check time on line %d.\n",config_line);
      boot_exit(1);	
      }
    return;

  case 15:
    if ((amsys->max_users=val)<1) {
      fprintf(stderr,"Lotos: Invalid value for max_users on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 16:
    if ((amsys->heartbeat=val)<1) {
      fprintf(stderr,"Lotos: Invalid value for heartbeat on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 17:
    if ((amsys->login_idle_time=val)<10) {
      fprintf(stderr,"Lotos: Invalid value for login_idle_time on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 18:
    if ((amsys->user_idle_time=val)<10) {
      fprintf(stderr,"Lotos: Invalid value for user_idle_time on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 19: 
    if ((amsys->password_echo=yn_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Password_echo must be YES or NO on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 20: 
    if ((amsys->ignore_sigterm=yn_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Ignore_sigterm must be YES or NO on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 21:
    if ((amsys->auto_connect=yn_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Auto_connect must be YES or NO on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 22:
    if ((amsys->max_clones=val)<0) {
      fprintf(stderr,"Lotos: Invalid value for max_clones on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 23:
    if ((amsys->ban_swearing=minmax_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Ban_swearing must be OFF, MIN or MAX on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 24:
    if (!strcmp(wrd[1],"NONE")) amsys->crash_action=0;
    else if (!strcmp(wrd[1],"IGNORE")) amsys->crash_action=1;
    else if (!strcmp(wrd[1],"REBOOT")) amsys->crash_action=2;
	else if (!strcmp(wrd[1],"RESTART")) amsys->crash_action=3;
	else if (!strcmp(wrd[1],"SHUTDOWN")) amsys->crash_action=4;
    else {
      fprintf(stderr,"Lotos: Crash_action must be NONE, IGNORE, REBOOT, RESTART or SHUTDOWN on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 25:
    if ((amsys->colour_def=onoff_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Colour_def must be ON or OFF on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 26:
    if ((amsys->time_out_afks=yn_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Time_out_afks must be YES or NO on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 27:
    if ((amsys->charecho_def=onoff_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Charecho_def must be ON or OFF on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 28:
    if ((amsys->time_out_maxlevel=get_level(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Unknown level specifier for time_out_maxlevel on line %d.\n",config_line);
      boot_exit(1);	
      }
    return;

  case 29: /* auto purge on boot up */
    if ((amsys->auto_purge=yn_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Auto_purge must be YES or NO on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 30: /* define whether auto promotes are on or off */
    if ((amsys->auto_promote=yn_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: auto_promote must be YES or NO on line %d.\n",config_line);
      boot_exit(1);
      } 
    return;

  case 31:
    if ((amsys->personal_rooms=yn_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Personal_rooms must be YES or NO on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 32:
    if ((amsys->random_motds=yn_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Random_motds must be YES or NO on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 33:
    if ((amsys->startup_room_parse=yn_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Startup_room_parse must be YES or NO on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 34: 
    if ((amsys->resolve_ip=resolve_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Resolve_ip must be OFF, AUTO or MANUAL on line %d.\n",config_line);
      boot_exit(1);
      }
    return;

  case 35: /* turns flood protection and auto-baning on and off */
    if ((amsys->flood_protect=onoff_check(wrd[1]))==-1) {
      fprintf(stderr,"Lotos: Flood_protect must be ON or OFF on line %d.\n",config_line);
      boot_exit(1);
      }
    return;
  
  case 36: /* povoli rozsirenie pre Pueblo */
#ifdef PUEBLO
    if ((syspp->pueblo_enh=onoff_check(wrd[1]))==-1) {
      fprintf(stderr, "Lotos: Pueblo_enh musi byt ON alebo OFF na riadku %d.\n", config_line);
      boot_exit(1);
      }
#endif
    return;

  case 37: /* perioda ukladania userfajlov v minutach */
    if (!is_inumber(wrd[1])) {
      fprintf(stderr, "Lotos: Auto_save na riadku %d musi byt cele kladne cislo alebo -1.\n", config_line);
      boot_exit(1);
      }
    syspp->auto_save=atoi(wrd[1]);
    if (syspp->auto_save==0 || syspp->auto_save<(-1)) {
      fprintf(stderr, "Lotos: Auto_save na riadku %d ma chybny parameter.\n", config_line);
      boot_exit(1);
      }
    return;
  case 38: /* default restrictions mask for superior users */
    strcpy(susers_restrict, wrd[1]);
    return;
  case 39: /* auto_afk */
    if (!is_number(wrd[1])) {
      	fprintf(stderr, "Lotos: Auto_afk na riadku %d musi byt cele kladne cislo\n", config_line);
      	boot_exit(1);
      	}
    syspp->auto_afk_time=atoi(wrd[1]);
    if (syspp->auto_afk_time>0) syspp->auto_afk=1;
    else syspp->auto_afk=0;
    return;
  case 40: /* use_hosts_file */
    if ((use_hostsfile=yn_check(wrd[1]))==-1) {
      fprintf(stderr, "Lotos: use_hosts_file musi byt YES alebo NO na riadku %d.\n", config_line);
      boot_exit(1);
      }
    return;

  } /* end switch */
}
示例#10
0
bool layer_raster::has_spatial_index(const frame& fr)
{
  size_t level(get_level(fr));
  auto tbl(get_table_def(level));
  return tbl.rtree(m_raster.levels[level].geometry.qualifier) != 0;
}
示例#11
0
double layer_raster::native_scale(const frame& fr)
{
  return m_raster.levels[get_level(fr)].resolution_x;
}
示例#12
0
short char_data::get_level( const char *what )
{
    short i = 0, max = 0;;

    if ( what == '\0' )
        return level;

    if ( !str_prefix(what, "maxmortal") )
    {
        for ( i = 0; i < MAX_CLASS; i++ )
            if ( lvl[i] > max )
                max = lvl[i];
        return max;
    }
    if ( !str_prefix(what, "maxremortal") )
    {
        for ( i = 0; i < MAX_CLASS; i++ )
            if ( lvl2[i] > max )
                max = lvl2[i];
        return max;
    }
    if ( !str_prefix(what, "mortal") )
        return (lvl[CLS_MAG] + lvl[CLS_CLE] + lvl[CLS_THI] + lvl[CLS_WAR] + lvl[CLS_PSI]);
    if ( !str_prefix(what, "remortal") )
        return (lvl2[CLS_SOR] + lvl2[CLS_MON] + lvl2[CLS_ASS] + lvl2[CLS_KNI] + lvl2[CLS_NEC]);
    if ( !str_prefix(what, "psuedo") )
    {
        if ( IS_NPC(this) )
            return get_level();
        else
        {
            if ( (get_level("remortal") / 4) > 0 )
                return (get_level() + (get_level("remortal") / 4));
            else
                return get_level();
        }
    }

    if ( !str_prefix(what, "adept") )
        return IS_NPC(this) ? get_level() / 7 : pcdata->adept_level;
    if ( !str_prefix(what, "mage") )
        return lvl[CLS_MAG];
    if ( !str_prefix(what, "cleric") )
        return lvl[CLS_CLE];
    if ( !str_prefix(what, "thief") )
        return lvl[CLS_THI];
    if ( !str_prefix(what, "warrior") )
        return lvl[CLS_WAR];
    if ( !str_prefix(what, "psionicist") )
        return lvl[CLS_PSI];
    if ( !str_prefix(what, "sorcerer") )
        return lvl2[CLS_SOR];
    if ( !str_prefix(what, "monk") )
        return lvl2[CLS_MON];
    if ( !str_prefix(what, "assassin") )
        return lvl2[CLS_ASS];
    if ( !str_prefix(what, "knight") )
        return lvl2[CLS_KNI];
    if ( !str_prefix(what, "necromancer") )
        return lvl2[CLS_NEC];

    snprintf(log_buf, (2 * MIL), "char_data::get_level(): Received invalid request for '%s'.", what);
    monitor_chan(log_buf, MONITOR_DEBUG);
    return level;
}
示例#13
0
const char *char_data::get_whoname( )
{
    char buf[MSL] = {'\0'};
    short s1, s2, s3, s4, s5;
    const char *output;

    if ( IS_NPC(this) )
        return "";

    if ( IS_IMMORTAL(this) )
    {
        if ( strcmp(pcdata->who_name,"off") )
            return pcdata->who_name;

        switch ( get_level() )
        {
            case MAX_LEVEL - 0: return "@@l~* CREATOR *~@@N ";
            case MAX_LEVEL - 1: return "@@B-* SUPREME *-@@N ";
            case MAX_LEVEL - 2: return "@@a-=MAJOR GOD=-@@N ";
            case MAX_LEVEL - 3: return "@@a--MINOR GOD--@@N ";
            case MAX_LEVEL - 4: return "@@c - IMMORTAL -@@N ";
        }
    }

    if ( IS_ADEPT(this) )
    {
        if ( strcmp(pcdata->who_name,"off") )
            return pcdata->who_name;

        switch ( get_level("adept") )
        {
            case 1:  return "@@W    Mystic    @@N";
            case 2:  return "@@a   Templar    @@N";
            case 3:  return "@@l Illusionist  @@N";
            case 4:  return "@@e   Crusader   @@N";
            case 5:  return "@@d   Warlock    @@N";
            case 6:  return "@@a   Paladin    @@N";
            case 7:  return "@@r    Ranger    @@N";
            case 8:  return "@@c  Gladiator   @@N";
            case 9:  return "@@l    Shogun    @@N";
            case 10: return "@@e    Shamen    @@N";
            case 11: return "@@r    Druid     @@N";
            case 12: return "@@b  Conjurer    @@N";
            case 13: return "@@l Elementalist @@N";
            case 14: return "@@m  Runemaster  @@N";
            case 15: return "@@d Shadowmaster @@N";
            case 16: return "@@b Beastmaster  @@N";
            case 17: return "@@R   Warlord    @@N";
            case 18: return "@@e  Dragonlord  @@N";
            case 19: return "@@d  Demonlord   @@N";
            case 20: return "@@m  Realm Lord  @@N";
        }
    }

    if ( IS_REMORT(this) )
    {
        s1 = get_level("sor"); s2 = get_level("mon"); s3 = get_level("ass"); s4 = get_level("kni"); s5 = get_level("nec");
        snprintf( buf, MSL, "@@m%2d %2d %2d %2d %2d@@N", s1 <= 0 ? 0 : s1, s2 <= 0 ? 0 : s2, s3 <= 0 ? 0 : s3, s4 <= 0 ? 0 : s4, s5 <= 0 ? 0 : s5 );
        output = str_dup( buf );

        return output;
    }
    else
    {
        s1 = get_level("mag"); s2 = get_level("cle"); s3 = get_level("thi"); s4 = get_level("war"); s5 = get_level("psi");
        snprintf( buf, MSL, "@@b%2d %2d %2d %2d %2d@@N", s1 <= 0 ? 0 : s1, s2 <= 0 ? 0 : s2, s3 <= 0 ? 0 : s3, s4 <= 0 ? 0 : s4, s5 <= 0 ? 0 : s5 );
        output = str_dup( buf );

        return output;
    }

    return "";
}
示例#14
0
文件: study.c 项目: Xolgrim/server
int learn_cmd(unit * u, order * ord)
{
    region *r = u->region;
    int p;
    magic_t mtyp;
    int l;
    int studycost, days;
    double multi = 1.0;
    attrib *a = NULL;
    teaching_info *teach = NULL;
    int money = 0;
    skill_t sk;
    int maxalchemy = 0;
    int speed_rule = (study_rule_t)get_param_int(global.parameters, "study.speedup", 0);
    static int learn_newskills = -1;
    if (learn_newskills < 0) {
        const char *str = get_param(global.parameters, "study.newskills");
        if (str && strcmp(str, "false") == 0)
            learn_newskills = 0;
        else
            learn_newskills = 1;
    }
    if (!unit_can_study(u)) {
        ADDMSG(&u->faction->msgs, msg_feedback(u, ord, "error_race_nolearn", "race",
            u_race(u)));
        return 0;
    }

    init_order(ord);
    sk = getskill(u->faction->locale);

    if (sk < 0) {
        cmistake(u, ord, 77, MSG_EVENT);
        return 0;
    }
    if (SkillCap(sk) && SkillCap(sk) <= effskill(u, sk)) {
        cmistake(u, ord, 771, MSG_EVENT);
        return 0;
    }
    /* Hack: Talente mit Malus -99 koennen nicht gelernt werden */
    if (u_race(u)->bonus[sk] == -99) {
        cmistake(u, ord, 771, MSG_EVENT);
        return 0;
    }
    if (learn_newskills == 0) {
        skill *sv = unit_skill(u, sk);
        if (sv == NULL) {
            /* we can only learn skills we already have */
            cmistake(u, ord, 771, MSG_EVENT);
            return 0;
        }
    }

    /* snotlings koennen Talente nur bis T8 lernen */
    if (u_race(u) == get_race(RC_SNOTLING)) {
        if (get_level(u, sk) >= 8) {
            cmistake(u, ord, 308, MSG_EVENT);
            return 0;
        }
    }

    p = studycost = study_cost(u, sk);
    a = a_find(u->attribs, &at_learning);
    if (a != NULL) {
        teach = (teaching_info *)a->data.v;
    }

    /* keine kostenpflichtigen Talente fuer Migranten. Vertraute sind
     * keine Migranten, wird in is_migrant abgefangen. Vorsicht,
     * studycost darf hier noch nicht durch Akademie erhoeht sein */
    if (studycost > 0 && !ExpensiveMigrants() && is_migrant(u)) {
        ADDMSG(&u->faction->msgs, msg_feedback(u, ord, "error_migrants_nolearn",
            ""));
        return 0;
    }
    /* Akademie: */
  {
      struct building *b = inside_building(u);
      const struct building_type *btype = b ? b->type : NULL;

      if (btype && btype == bt_find("academy")) {
          studycost = _max(50, studycost * 2);
      }
  }

  if (sk == SK_MAGIC) {
      if (u->number > 1) {
          cmistake(u, ord, 106, MSG_MAGIC);
          return 0;
      }
      if (is_familiar(u)) {
          /* Vertraute zaehlen nicht zu den Magiern einer Partei,
           * koennen aber nur Graue Magie lernen */
          mtyp = M_GRAY;
          if (!is_mage(u))
              create_mage(u, mtyp);
      }
      else if (!has_skill(u, SK_MAGIC)) {
          int mmax = skill_limit(u->faction, SK_MAGIC);
          /* Die Einheit ist noch kein Magier */
          if (count_skill(u->faction, SK_MAGIC) + u->number > mmax) {
              ADDMSG(&u->faction->msgs, msg_feedback(u, ord, "error_max_magicians",
                  "amount", mmax));
              return 0;
          }
          mtyp = getmagicskill(u->faction->locale);
          if (mtyp == M_NONE || mtyp == M_GRAY) {
              /* wurde kein Magiegebiet angegeben, wird davon
               * ausgegangen, dass das normal gelernt werden soll */
              if (u->faction->magiegebiet != 0) {
                  mtyp = u->faction->magiegebiet;
              }
              else {
                  /* Es wurde kein Magiegebiet angegeben und die Partei
                   * hat noch keins gewaehlt. */
                  mtyp = getmagicskill(u->faction->locale);
                  if (mtyp == M_NONE) {
                      cmistake(u, ord, 178, MSG_MAGIC);
                      return 0;
                  }
              }
          }
          if (mtyp != u->faction->magiegebiet) {
              /* Es wurde versucht, ein anderes Magiegebiet zu lernen
               * als das der Partei */
              if (u->faction->magiegebiet != 0) {
                  cmistake(u, ord, 179, MSG_MAGIC);
                  return 0;
              }
              else {
                  /* Lernt zum ersten mal Magie und legt damit das
                   * Magiegebiet der Partei fest */
                  u->faction->magiegebiet = mtyp;
              }
          }
          if (!is_mage(u))
              create_mage(u, mtyp);
      }
      else {
          /* ist schon ein Magier und kein Vertrauter */
          if (u->faction->magiegebiet == 0) {
              /* die Partei hat noch kein Magiegebiet gewaehlt. */
              mtyp = getmagicskill(u->faction->locale);
              if (mtyp == M_NONE) {
                  mtyp = getmagicskill(u->faction->locale);
                  if (mtyp == M_NONE) {
                      cmistake(u, ord, 178, MSG_MAGIC);
                      return 0;
                  }
              }
              /* Legt damit das Magiegebiet der Partei fest */
              u->faction->magiegebiet = mtyp;
          }
      }
  }
  if (sk == SK_ALCHEMY) {
      maxalchemy = eff_skill(u, SK_ALCHEMY, r);
      if (!has_skill(u, SK_ALCHEMY)) {
          int amax = skill_limit(u->faction, SK_ALCHEMY);
          if (count_skill(u->faction, SK_ALCHEMY) + u->number > amax) {
              ADDMSG(&u->faction->msgs, msg_feedback(u, ord, "error_max_alchemists",
                  "amount", amax));
              return 0;
          }
      }
  }
  if (studycost) {
      int cost = studycost * u->number;
      money = get_pooled(u, get_resourcetype(R_SILVER), GET_DEFAULT, cost);
      money = _min(money, cost);
  }
  if (money < studycost * u->number) {
      studycost = p;              /* Ohne Univertreurung */
      money = _min(money, studycost);
      if (p > 0 && money < studycost * u->number) {
          cmistake(u, ord, 65, MSG_EVENT);
          multi = money / (double)(studycost * u->number);
      }
  }

  if (teach == NULL) {
      a = a_add(&u->attribs, a_new(&at_learning));
      teach = (teaching_info *)a->data.v;
      teach->teachers[0] = 0;
  }
  if (money > 0) {
      use_pooled(u, get_resourcetype(R_SILVER), GET_DEFAULT, money);
      ADDMSG(&u->faction->msgs, msg_message("studycost",
          "unit region cost skill", u, u->region, money, sk));
  }

  if (get_effect(u, oldpotiontype[P_WISE])) {
      l = _min(u->number, get_effect(u, oldpotiontype[P_WISE]));
      teach->value += l * 10;
      change_effect(u, oldpotiontype[P_WISE], -l);
  }
  if (get_effect(u, oldpotiontype[P_FOOL])) {
      l = _min(u->number, get_effect(u, oldpotiontype[P_FOOL]));
      teach->value -= l * 30;
      change_effect(u, oldpotiontype[P_FOOL], -l);
  }

  if (p != studycost) {
      /* ist_in_gebaeude(r, u, BT_UNIVERSITAET) == 1) { */
      /* p ist Kosten ohne Uni, studycost mit; wenn
       * p!=studycost, ist die Einheit zwangsweise
       * in einer Uni */
      teach->value += u->number * 10;
  }

  if (is_cursed(r->attribs, C_BADLEARN, 0)) {
      teach->value -= u->number * 10;
  }

  multi *= study_speedup(u, sk, speed_rule);
  days = study_days(u, sk);
  days = (int)((days + teach->value) * multi);

  /* the artacademy currently improves the learning of entertainment
     of all units in the region, to be able to make it cumulative with
     with an academy */

  if (sk == SK_ENTERTAINMENT
      && buildingtype_exists(r, bt_find("artacademy"), false)) {
      days *= 2;
  }

  if (fval(u, UFL_HUNGER))
      days /= 2;

  while (days) {
      if (days >= u->number * 30) {
          learn_skill(u, sk, 1.0);
          days -= u->number * 30;
      }
      else {
          double chance = (double)days / u->number / 30;
          learn_skill(u, sk, chance);
          days = 0;
      }
  }
  if (a != NULL) {
      if (teach != NULL) {
          int index = 0;
          while (teach->teachers[index] && index != MAXTEACHERS) {
              unit *teacher = teach->teachers[index++];
              if (teacher->faction != u->faction) {
                  bool feedback = alliedunit(u, teacher->faction, HELP_GUARD);
                  if (feedback) {
                      ADDMSG(&teacher->faction->msgs, msg_message("teach_teacher",
                          "teacher student skill level", teacher, u, sk,
                          effskill(u, sk)));
                  }
                  ADDMSG(&u->faction->msgs, msg_message("teach_student",
                      "teacher student skill", teacher, u, sk));
              }
          }
      }
      a_remove(&u->attribs, a);
      a = NULL;
  }
  fset(u, UFL_LONGACTION | UFL_NOTMOVING);

  /* Anzeigen neuer Traenke */
  /* Spruchlistenaktualiesierung ist in Regeneration */

  if (sk == SK_ALCHEMY) {
      const potion_type *ptype;
      faction *f = u->faction;
      int skill = eff_skill(u, SK_ALCHEMY, r);
      if (skill > maxalchemy) {
          for (ptype = potiontypes; ptype; ptype = ptype->next) {
              if (skill == ptype->level * 2) {
                  attrib *a = a_find(f->attribs, &at_showitem);
                  while (a && a->type == &at_showitem && a->data.v != ptype)
                      a = a->next;
                  if (a == NULL || a->type != &at_showitem) {
                      a = a_add(&f->attribs, a_new(&at_showitem));
                      a->data.v = (void *)ptype->itype;
                  }
              }
          }
      }
  }
  else if (sk == SK_MAGIC) {
      sc_mage *mage = get_mage(u);
      if (!mage) {
          mage = create_mage(u, u->faction->magiegebiet);
      }
  }

  return 0;
}