Exemple #1
0
APU_DECLARE(apr_status_t) apr_reslist_acquire(apr_reslist_t *reslist,
                                              void **resource)
{
    apr_status_t rv;
    apr_res_t *res;

    apr_thread_mutex_lock(reslist->listlock);
    /* If there are idle resources on the available list, use
     * them right away. */
    if (reslist->nidle > 0) {
        /* Pop off the first resource */
        res = pop_resource(reslist);
        *resource = res->opaque;
        free_container(reslist, res);
        apr_thread_mutex_unlock(reslist->listlock);
        return APR_SUCCESS;
    }
    /* If we've hit our max, block until we're allowed to create
     * a new one, or something becomes free. */
    else while (reslist->ntotal >= reslist->hmax
                && reslist->nidle <= 0) {
        if (reslist->timeout) {
            if ((rv = apr_thread_cond_timedwait(reslist->avail, 
                reslist->listlock, reslist->timeout)) != APR_SUCCESS) {
                apr_thread_mutex_unlock(reslist->listlock);
                return rv;
            }
        }
        else
            apr_thread_cond_wait(reslist->avail, reslist->listlock);
    }
    /* If we popped out of the loop, first try to see if there
     * are new resources available for immediate use. */
    if (reslist->nidle > 0) {
        res = pop_resource(reslist);
        *resource = res->opaque;
        free_container(reslist, res);
        apr_thread_mutex_unlock(reslist->listlock);
        return APR_SUCCESS;
    }
    /* Otherwise the reason we dropped out of the loop
     * was because there is a new slot available, so create
     * a resource to fill the slot and use it. */
    else {
        rv = create_resource(reslist, &res);
        if (rv == APR_SUCCESS) {
            reslist->ntotal++;
            *resource = res->opaque;
        }
        free_container(reslist, res);
        apr_thread_mutex_unlock(reslist->listlock);
        return rv;
    }
}
Exemple #2
0
static apr_status_t reslist_cleanup(void *data_)
{
    apr_status_t rv;
    apr_reslist_t *rl = data_;
    apr_res_t *res;

    apr_thread_mutex_lock(rl->listlock);

    while (rl->nidle > 0) {
        res = pop_resource(rl);
        rl->ntotal--;
        rv = destroy_resource(rl, res);
        if (rv != APR_SUCCESS) {
            return rv;
        }
        free_container(rl, res);
    }

    assert(rl->nidle == 0);
    assert(rl->ntotal == 0);

    apr_thread_mutex_destroy(rl->listlock);
    apr_thread_cond_destroy(rl->avail);

    return APR_SUCCESS;
}
int main()
{
  IntContainer *z;
  uint64_t val;
  z = malloc(sizeof(IntContainer));
  z->x = (uint64_t) z;
  free_container(z);
  free(z);
  return 0;
}
Exemple #4
0
/*
 * We must ensure a container is either in the buffer or written to disks.
 */
static void* append_thread(void *arg) {

	while (1) {
		struct container *c = sync_queue_get_top(container_buffer);
		if (c == NULL)
			break;

		TIMER_DECLARE(1);
		TIMER_BEGIN(1);

		write_container(c);

		TIMER_END(1, jcr.write_time);

		sync_queue_pop(container_buffer);

		free_container(c);
	}

	return NULL;
}
int send_data_from_obj(struct request *rq, struct mem_obj *obj)
{
    struct buff * tmp=NULL;//obj->container;
    struct	av *header=obj->headers;
    struct buff *hdrs_to_send=alloc_buff(CHUNK_SIZE); /* most headers fit this (?) */
//	rq->server->set_time(60);
    char tmp_str[100];
    int start=0,send_len=obj->content_length;
    pthread_mutex_lock(&obj->lock);
    if(!swap_in_obj(obj) ) {
        pthread_mutex_unlock(&obj->lock);
        dead_obj(obj);
        goto error;
    }
    pthread_mutex_unlock(&obj->lock);
    tmp=obj->container;
    if(rq->range_to==-1)
        rq->range_to=obj->content_length-1;
    if ( TEST(rq->flags, RQ_HAVE_RANGE)) {
        if(   // &&  (obj->state == OBJ_READY)
            // &&  !content_chunked(obj)
            ((rq->range_from >= 0 && rq->range_from<obj->content_length-1)
             && (rq->range_to == -1||rq->range_to>rq->range_from) )) {
            attach_av_pair_to_buff("HTTP/1.1","206 Partial Content",hdrs_to_send);
            memset(tmp_str,0,sizeof(tmp_str));
            snprintf(tmp_str,sizeof(tmp_str)-1,"%d-%d/%d",rq->range_from,rq->range_to,obj->content_length);
            /*
            if(rq->range_to!=-1)
            	snprintf(tmp_str+strlen(tmp_str),sizeof(tmp_str)-1-strlen(tmp_str),"%d",MIN(rq->range_to,obj->content_length-1));
            snprintf(tmp_str+strlen(tmp_str),sizeof(tmp_str)-1-strlen(tmp_str),"/%d",obj->content_length);
            */
            attach_av_pair_to_buff("Content-Range:",tmp_str,hdrs_to_send);
            header=header->next;
            start=rq->range_from;
            if(rq->range_to>=0)
                send_len=MIN(rq->range_to+1,obj->content_length)-rq->range_from;
            else
                send_len=obj->content_length-rq->range_from;
        } else if(rq->range_from>obj->content_length-1) {
            attach_av_pair_to_buff("HTTP/1.1","416 Requested Range Not Satisfiable",hdrs_to_send);
            memset(tmp_str,0,sizeof(tmp_str));
            snprintf(tmp_str,sizeof(tmp_str)-1,"*/%d",obj->content_length);
            attach_av_pair_to_buff("Content-Range:",tmp_str,hdrs_to_send);
            start=-1;
            header=header->next;
        }
    }

    while(header) {
//		printf("attr=%s\n",header->attr);
        if(strncasecmp(header->attr,"Connection:",11)==0) {
            if(!TEST(rq->flags,RQ_HAS_KEEP_CONNECTION)) {
                attach_av_pair_to_buff("Connection:","close",hdrs_to_send);
            } else {
                attach_av_pair_to_buff("Connection:","keep-alive",hdrs_to_send);
            }
            goto next_head;
        }
        if(strncasecmp(header->attr,"Server:",7)==0) {
            memset(tmp_str,0,sizeof(tmp_str));
            snprintf(tmp_str,sizeof(tmp_str)-1,"kingate/%s (cached)",VER_ID);
            attach_av_pair_to_buff("Server:",tmp_str,hdrs_to_send);
            goto next_head;
        }
        attach_av_pair_to_buff(header->attr, header->val, hdrs_to_send);
next_head:
        header = header->next;
    }
    attach_av_pair_to_buff("", "", hdrs_to_send);
    if(rq->server->send(hdrs_to_send->data,hdrs_to_send->used)<=0)
        goto done;
//	printf("start=%d,send_len=%d.\n",start,send_len);
    if(start==-1)
        goto done;
    while(tmp!=NULL) {
        if(tmp->used<start) {
            start-=tmp->used;
            goto next_buffer;
        }
        if(send_len<=0)
            break;
        if(rq->server->send(tmp->data+start,MIN(tmp->used,send_len))<=0)
            goto error;
        start=0;
        send_len-=tmp->used;
next_buffer:
        tmp=tmp->next;
    }
done:
    if(hdrs_to_send)
        free_container(hdrs_to_send);
    return SEND_FROM_MEM_OK;
error:
    if(hdrs_to_send)
        free_container(hdrs_to_send);
    return CONNECT_ERR;
}
static int load_head(struct request *rq,struct mem_obj *obj,head_info &m_head)
{
    //char	*answer = NULL;
    struct	server_answ	answ_state;
    struct pollarg pollarg[2];
    struct	av		*header = NULL;
    int r=0,downgrade_flags=0;
    char *answer= (char *)malloc(ANSW_SIZE+1);
    char *buf=answer;
    int len=ANSW_SIZE;
    int head_status=CONNECT_ERR;
    struct	buff	*hdrs_to_send=NULL;
//	rq->client->set_time(0);
//	rq->server->set_time(0);
    if ( !answer )
        goto error;
    memset(&answ_state,0, sizeof(answ_state));
    pollarg[0].fd = rq->client->get_socket();
    pollarg[0].request = FD_POLL_RD;
    pollarg[1].fd = rq->server->get_socket();
    pollarg[1].request = FD_POLL_RD;
    forever() {
        if((r = poll_descriptors(2, &pollarg[0], conf.time_out[HTTP]*1000))<=0) {
            klog(DEBUG_LOG,"poll descriptors is error in file %s line %d\n",__FILE__,__LINE__);
            goto error;
        }
        if(IS_READABLE(&pollarg[1]) || IS_HUPED(&pollarg[1])) {
            klog(DEBUG_LOG,"prev head value=%d,client close the connection\n",head_status);
            //head_status=CLIENT_HAVE_DATA;
            goto error;
        }
        if(IS_READABLE(&pollarg[0]))
            r = rq->client->recv_t(buf,len,0);
        else {
            klog(DEBUG_LOG,"unknow error is happen\n");
            goto error;
        }
        if ( r <= 0  ) {
            klog(DEBUG_LOG,"recv server data error\n");
            goto error;
        }
//		buf[r]=0;
//		printf("%s",buf);
        buf+=r;
        len-=r;
        if ( !(answ_state.state & GOT_HDR) ) {
            obj->size += r;
            if ( check_server_headers(&answ_state, obj, answer,r, rq) ) {
                head_status=HEAD_UNKNOW;
                rq->flags|=RESULT_CLOSE;
                //	printf("%s:%d\n",__FILE__,__LINE__);
                goto send_data;
            }

        }
        if ( answ_state.state & GOT_HDR ) {

            obj->flags|= answ_state.flags;
            obj->times = answ_state.times;
//			printf("obj->times.last_modified=%d\n",obj->times.last_modified);
            if ( !obj->times.date )
                obj->times.date = global_sec_timer;
            //	check_new_object_expiration(rq, obj);
            obj->status_code = answ_state.status_code;
            if ( obj->status_code != STATUS_OK && obj->status_code!=STATUS_NOT_MODIFIED) {
                //	printf("status is not ok\n");
                //	printf("obj->status_code=%d.\n",obj->status_code);
                rq->flags|=RESULT_CLOSE;
                head_status=HEAD_NOT_OK;
                goto send_data;
            }
            //	obj->flags |= FLAG_DEAD;
            if (TEST(obj->flags , ANSW_NO_STORE) ) {
                //printf("answer is no cache\n");
                head_status=HEAD_OK_NO_STORE;
                rq->flags|=RESULT_CLOSE;
                goto send_data;
            }
            //		obj->flags |= ANSW_NO_CACHE;
            //	downgrade_flags = downgrade(rq, obj);
            //	my_xlog(OOPS_LOG_HTTP|OOPS_LOG_DBG, "fill_mem_obj(): Downgrade flags: %x\n", downgrade_flags);
            hdrs_to_send = alloc_buff(CHUNK_SIZE); /* most headers fit this (?) */
            if ( !hdrs_to_send ) goto error;
            header = obj->headers;

            if ( !header ) {
                rq->flags|=RESULT_CLOSE;
                goto send_data ;
            }

            if ( TEST(obj->flags, ANSW_SHORT_CONTAINER) ) {
                //printf("answer is short contaner\n");
                head_status=HEAD_OK_NO_STORE;
                rq->flags|=RESULT_CLOSE;
                goto send_data;
            }
            /* first must be "HTTP/1.x 200 ..." */
            /*	if ( TEST(downgrade_flags, DOWNGRADE_ANSWER) ) {
            		attach_av_pair_to_buff("HTTP/1.0", header->val, hdrs_to_send);
            		header = header->next;
            	}
            */	while(header) {
                if(strncasecmp(header->attr,"Set-Cookie:",7)!=0) { //don't cache cookie
                    if(strncasecmp(header->attr,"Connection:",11)==0) {
                        if(!TEST(rq->flags,RQ_HAS_KEEP_CONNECTION)) {
                            attach_av_pair_to_buff("Connection:","close",hdrs_to_send);
                        } else {
                            attach_av_pair_to_buff("Connection:","keep-alive",hdrs_to_send);
                        }
                        goto next_header;
                    }
                } else {
                    //	printf("server has set-cookie\n");
                    head_status=HEAD_OK_NO_STORE;
                    rq->flags|=RESULT_CLOSE;
                    goto send_data;
                }
                attach_av_pair_to_buff(header->attr, header->val, hdrs_to_send);
next_header:
                header = header->next;
            }
            attach_av_pair_to_buff("", "", hdrs_to_send);
            //	obj->container=hdrs_to_send;
            //	hdrs_to_send->next=obj->hot_buff;
            if(obj->status_code==STATUS_NOT_MODIFIED) {
                head_status=HEAD_NOT_MODIFIED;
                m_head.head=hdrs_to_send->data;
                m_head.len=hdrs_to_send->used;
                hdrs_to_send->data=NULL;
                //	free_container(hdrs_to_send);
                goto done;
            }
            //	obj->container=obj->hot_buff;

            if(rq->server->send(hdrs_to_send->data,hdrs_to_send->used)<0) {
                //	free_container(hdrs_to_send);
                goto error;
            }
            //	free_container(hdrs_to_send);
            //		printf("%s\n",hdrs_to_send->data);
            head_status=HEAD_OK;
            goto done;
        }
        if(len<1) {
            //	printf("head size is too large\n");
            head_status=HEAD_UNKNOW;
            rq->flags|=RESULT_CLOSE;
            goto send_data;//head size is too large
        }

    }

error://get head failed
    obj->flags |= FLAG_DEAD;
    if(hdrs_to_send)
        free_container(hdrs_to_send);
    IF_FREE(answer);
    return head_status;
done://get head ok;
    if(hdrs_to_send)
        free_container(hdrs_to_send);
    free(answer);
    return head_status;
send_data://得到头失败,但要转发数据
    if(hdrs_to_send)
        free_container(hdrs_to_send);
    m_head.head=answer;
    m_head.len=ANSW_SIZE-len;
    answer[m_head.len]=0;
    return head_status;
}
Exemple #7
0
/**
 * Perform routine maintenance on the resource list. This call
 * may instantiate new resources or expire old resources.
 */
static apr_status_t reslist_maint(apr_reslist_t *reslist)
{
    apr_time_t now;
    apr_status_t rv;
    apr_res_t *res;
    int created_one = 0;

    apr_thread_mutex_lock(reslist->listlock);

    /* Check if we need to create more resources, and if we are allowed to. */
    while (reslist->nidle < reslist->min && reslist->ntotal < reslist->hmax) {
        /* Create the resource */
        rv = create_resource(reslist, &res);
        if (rv != APR_SUCCESS) {
            free_container(reslist, res);
            apr_thread_mutex_unlock(reslist->listlock);
            return rv;
        }
        /* Add it to the list */
        push_resource(reslist, res);
        /* Update our counters */
        reslist->ntotal++;
        /* If someone is waiting on that guy, wake them up. */
        rv = apr_thread_cond_signal(reslist->avail);
        if (rv != APR_SUCCESS) {
            apr_thread_mutex_unlock(reslist->listlock);
            return rv;
        }
        created_one++;
    }

    /* We don't need to see if we're over the max if we were under it before */
    if (created_one) {
        apr_thread_mutex_unlock(reslist->listlock);
        return APR_SUCCESS;
    }

    /* Check if we need to expire old resources */
    now = apr_time_now();
    while (reslist->nidle > reslist->smax && reslist->nidle > 0) {
        /* Peak at the last resource in the list */
        res = APR_RING_LAST(&reslist->avail_list);
        /* See if the oldest entry should be expired */
        if (now - res->freed < reslist->ttl) {
            /* If this entry is too young, none of the others
             * will be ready to be expired either, so we are done. */
            break;
        }
        APR_RING_REMOVE(res, link);
        reslist->nidle--;
        reslist->ntotal--;
        rv = destroy_resource(reslist, res);
        free_container(reslist, res);
        if (rv != APR_SUCCESS) {
            apr_thread_mutex_unlock(reslist->listlock);
            return rv;
        }
    }

    apr_thread_mutex_unlock(reslist->listlock);
    return APR_SUCCESS;
}
Exemple #8
0
int
ssm_build_container_table()
{
	int		i, j, k, ret = 0;
	ssm_node_t	*node;
	ssm_lun_t	*disk;
	ssm_container_t	*container;


	/*
	 * TODO: Use the minimal size of the disk for now.
	 */
	ssm_ctn_col_sz = ssm_resource.sr_min_size;
	ssm_ctn_ncols = ssm_data_nvecs + ssm_parity_nvecs;
	ssm_ctn_unit_sz = SSM_CTN_UNIT_SIZE_DEFAULT;

	/*
	 * Initialize disk block usage map for each disk
	 */
	for (i = 0; i < ssm_resource.sr_nnodes; i++) {
		node = ssm_resource.sr_node[i];
		for (j = 0; j < node->sn_ndisks; j++) {
			disk = node->sn_disks[j];
			disk->sl_nblocks = disk->sl_size / ssm_ctn_col_sz;
			disk->sl_blksz = ssm_ctn_col_sz;
			disk->sl_blockmap = (unsigned char *)
				malloc(disk->sl_nblocks *
				       sizeof(unsigned char));
			if (!disk->sl_blockmap) {
				fprintf(stderr,	"Failed to allocate memory "
					"for disk block usage map.\n");
				return ENOMEM;
			}

			for (k = 0; k < disk->sl_nblocks; k++) {
				disk->sl_blockmap[k] = SSM_BLOCK_FREE;
			}
		}
	}

	ssm_print_disk_usage();

	while (1) {
		container = create_container();
		if (!container) {
			break;
		}

		ssm_print_container(stdout, ssm_ctn_tbl.scb_entries, container);
		ssm_print_disk_usage();

		if (ssm_ctn_tbl.scb_entries == 0) {
			ssm_ctn_tbl.scb_ctn = (ssm_container_t **)
				malloc(sizeof(ssm_container_t *));
		} else {
			ssm_ctn_tbl.scb_ctn = (ssm_container_t **)
				realloc(ssm_ctn_tbl.scb_ctn,
					(ssm_ctn_tbl.scb_entries + 1) *
					sizeof(ssm_container_t *));
		}
		if (!ssm_ctn_tbl.scb_ctn) {
			fprintf(stderr, "Failed to allocate memory for "
				"the container table.\n");
			free_container(container);
			ret = ENOMEM;
			break;
		}
		ssm_ctn_tbl.scb_ctn[ssm_ctn_tbl.scb_entries++] = container;
	}

	return ret;
}
Exemple #9
0
/*
 * Create a single container
 * Returns a pointer to container if successfull
 * Returns NULL if failed
 */
static ssm_container_t *
create_container()
{
	int		i, ret;
	ssm_container_t	*container = NULL;

	/*
	 * Allocate one container
	 */
	container = (ssm_container_t *)malloc(sizeof(ssm_container_t));
	if (!container) {
		fprintf(stderr,	"Failed to allocate memory for a container.\n");
		return NULL;
	}

	ret = ssm_guid_create(&container->sc_guid);
	if (ret != 0 ) {
		fprintf(stderr,	"Failed to generate guid for a container.\n");
		free(container);
		return NULL;
	}

	container->sc_genid = 0;
	container->sc_owner = this_node.sn_hostid;
	container->sc_colsz = ssm_ctn_col_sz * 1024;
	container->sc_unitsz = ssm_ctn_unit_sz;
	container->sc_ncols = ssm_ctn_ncols;

	container->sc_col = (ssm_column_t *)malloc(container->sc_ncols *
						  sizeof(ssm_column_t));
	if (!container->sc_col) {
		fprintf(stderr,	"Failed to allocate memory for columns.\n");
		free(container);
		return NULL;
	}

	bzero(container->sc_col, container->sc_ncols * sizeof(ssm_column_t));

	/*
	 * Try to allocate the first column from this node
	 */
	ret = alloc_column_from_node(&this_node, &container->sc_col[0]);
	if (ret) {
		free_container(container);
		return NULL;
	}

	/*
	 * Continue with the rest of the columns
	 */
	for (i = 1; i < container->sc_ncols; i++){
		ret = alloc_column_from_any(&container->sc_col[i]);
		if (ret) {
			free_container(container);
			return NULL;
		}
	}

	/*
	 * Allocate and initialize the space bitmap
	 */
	container->sc_space_bmap = ctn_space_bmap_init(container->sc_colsz,
						       container->sc_unitsz);
	container->sc_space_avail = container->sc_space_bmap->sb_nbit;

	return container;
}