static int noit_fq_submit(iep_thread_driver_t *dr, const char *payload, size_t payloadlen) { int i; struct fq_driver *driver = (struct fq_driver *)dr; const char *routingkey = driver->routingkey; fq_msg *msg; if(*payload == 'M' || *payload == 'S' || *payload == 'C' || (*payload == 'B' && (payload[1] == '1' || payload[1] == '2'))) { char uuid_str[32 * 2 + 1]; int account_id, check_id; if(extract_uuid_from_jlog(payload, payloadlen, &account_id, &check_id, uuid_str)) { if(*routingkey) { char *replace; int newlen = strlen(driver->routingkey) + 1 + sizeof(uuid_str) + 2 * 32; replace = alloca(newlen); snprintf(replace, newlen, "%s.%x.%x.%d.%d%s", driver->routingkey, account_id%16, (account_id/16)%16, account_id, check_id, uuid_str); routingkey = replace; } } } /* Setup our message */ msg = fq_msg_alloc(payload, payloadlen); if(msg == NULL) { driver->allocation_failures++; return -1; } driver->msg_cnt++; fq_msg_exchange(msg, driver->exchange, strlen(driver->exchange)); noitL(noit_debug, "route[%s] -> %s\n", driver->exchange, routingkey); fq_msg_route(msg, routingkey, strlen(routingkey)); fq_msg_id(msg, NULL); for(i=0; i<driver->nhosts; i++) { if(fq_client_publish(driver->client[i], msg) == 1) BUMPSTAT(i, publications); else BUMPSTAT(i, client_tx_drop); } fq_msg_deref(msg); return 0; }
static int noit_rabbimq_connect(iep_thread_driver_t *dr) { struct amqp_driver *driver = (struct amqp_driver *)dr; if(!driver->connection) { int sidx = driver->nconnects++ % driver->nhosts; struct timeval timeout; amqp_rpc_reply_t r, *rptr; mtevL(mtev_error, "AMQP connect: %s:%d\n", driver->hostname[sidx], driver->port); BUMPSTAT(connects); driver->hostidx = sidx; timeout.tv_sec = driver->heartbeat; timeout.tv_usec = 0; driver->sockfd = amqp_open_socket(driver->hostname[sidx], driver->port, &timeout); if(driver->sockfd < 0) { mtevL(mtev_error, "AMQP connect failed: %s:%d\n", driver->hostname[sidx], driver->port); return -1; } if(setsockopt(driver->sockfd, SOL_SOCKET, SO_SNDBUF, &desired_sndbuf, sizeof(desired_sndbuf)) < 0) mtevL(mtev_debug, "rabbitmq: setsockopt(SO_SNDBUF, %ld) -> %s\n", (long int)desired_sndbuf, strerror(errno)); if(setsockopt(driver->sockfd, SOL_SOCKET, SO_RCVBUF, &desired_rcvbuf, sizeof(desired_rcvbuf)) < 0) mtevL(mtev_debug, "rabbitmq: setsockopt(SO_RCVBUF, %ld) -> %s\n", (long int)desired_rcvbuf, strerror(errno)); driver->has_error = 0; driver->connection = amqp_new_connection(); amqp_set_basic_return_cb(driver->connection, noit_rabbitmq_brcb, driver); amqp_set_sockfd(driver->connection, driver->sockfd); r = amqp_login(driver->connection, driver->vhost, 0, 131072, driver->heartbeat, AMQP_SASL_METHOD_PLAIN, driver->username, driver->password); if(r.reply_type != AMQP_RESPONSE_NORMAL) { mtevL(mtev_error, "AMQP login failed\n"); amqp_connection_close(driver->connection, AMQP_REPLY_SUCCESS); amqp_destroy_connection(driver->connection); if(driver->sockfd >= 0) close(driver->sockfd); driver->sockfd = -1; driver->connection = NULL; return -1; } amqp_channel_open(driver->connection, 1); rptr = amqp_get_rpc_reply(); if(rptr->reply_type != AMQP_RESPONSE_NORMAL) { mtevL(mtev_error, "AMQP channe_open failed\n"); amqp_connection_close(driver->connection, AMQP_REPLY_SUCCESS); amqp_destroy_connection(driver->connection); if(driver->sockfd >= 0) close(driver->sockfd); driver->sockfd = -1; driver->connection = NULL; return -1; } mtev_gettimeofday(&driver->last_hb, NULL); return 0; } /* 1 means already connected */ return 1; }
static int noit_rabbimq_submit(iep_thread_driver_t *dr, const char *payload, size_t payloadlen) { int rv; amqp_bytes_t body; struct amqp_driver *driver = (struct amqp_driver *)dr; const char *routingkey = driver->routingkey; body.len = payloadlen; body.bytes = (char *)payload; if(*payload == 'M' || *payload == 'S' || *payload == 'C' || (*payload == 'H' && payload[1] == '1') || (*payload == 'F' && payload[1] == '1') || (*payload == 'B' && (payload[1] == '1' || payload[1] == '2'))) { char uuid_str[32 * 2 + 1]; int account_id, check_id; if(extract_uuid_from_jlog(payload, payloadlen, &account_id, &check_id, uuid_str)) { if(*routingkey) { char *replace; int newlen = strlen(driver->routingkey) + 1 + sizeof(uuid_str) + 2 * 32; replace = alloca(newlen); snprintf(replace, newlen, "%s.%x.%x.%d.%d%s", driver->routingkey, account_id%16, (account_id/16)%16, account_id, check_id, uuid_str); routingkey = replace; } } } rv = amqp_basic_publish(driver->connection, 1, amqp_cstring_bytes(driver->exchange), amqp_cstring_bytes(routingkey), 1, 0, NULL, body); if(rv < 0) { mtevL(mtev_error, "AMQP publish failed, disconnecting\n"); amqp_connection_close(driver->connection, AMQP_REPLY_SUCCESS); amqp_destroy_connection(driver->connection); if(driver->sockfd >= 0) close(driver->sockfd); driver->sockfd = -1; driver->connection = NULL; return -1; } BUMPSTAT(publications); noit_rabbitmq_heartbeat(driver); noit_rabbitmq_read_frame(driver); amqp_maybe_release_buffers(driver->connection); if(driver->has_error) { amqp_connection_close(driver->connection, AMQP_REPLY_SUCCESS); amqp_destroy_connection(driver->connection); if(driver->sockfd >= 0) close(driver->sockfd); driver->sockfd = -1; driver->connection = NULL; return -1; } return 0; }
static void noit_rabbitmq_read_frame(struct amqp_driver *dr) { struct pollfd p; if(!dr->connection) return; while(1) { memset(&p, 0, sizeof(p)); p.fd = dr->sockfd; p.events = POLLIN; if(poll(&p, 1, 0)) { int rv; amqp_frame_t f; rv = amqp_simple_wait_frame(dr->connection, &f); if(rv > 0) { if(f.frame_type == AMQP_FRAME_HEARTBEAT) { BUMPSTAT(inbound_heartbeats); mtevL(mtev_debug, "amqp <- hearbeat\n"); } else if(f.frame_type == AMQP_FRAME_METHOD) { BUMPSTAT(inbound_methods); mtevL(mtev_error, "amqp <- method [%s]\n", amqp_method_name(f.payload.method.id)); dr->has_error = 1; switch(f.payload.method.id) { case AMQP_CHANNEL_CLOSE_METHOD: { amqp_channel_close_t *m = (amqp_channel_close_t *) f.payload.method.decoded; mtevL(mtev_error, "AMQP channel close error %d: %s\n", m->reply_code, (char *)m->reply_text.bytes); } break; case AMQP_CONNECTION_CLOSE_METHOD: { amqp_connection_close_t *m = (amqp_connection_close_t *) f.payload.method.decoded; mtevL(mtev_error, "AMQP connection close error %d: %s\n", m->reply_code, (char *)m->reply_text.bytes); } break; } } else { mtevL(mtev_error, "amqp <- frame [%d]\n", f.frame_type); } } else break; } else break; } }
static void fq_logger(fq_client c, const char *err) { int i; noitL(nlerr, "fq: %s\n", err); for(i=0;i<global_fq_ctx.nhosts;i++) { if(c == global_fq_ctx.client[i]) { BUMPSTAT(i, error_messages); break; } } }
static int noit_rabbimq_connect(iep_thread_driver_t *dr) { struct amqp_driver *driver = (struct amqp_driver *)dr; if(!driver->connection) { int sidx = driver->nconnects++ % driver->nhosts; struct timeval timeout; amqp_rpc_reply_t r, *rptr; noitL(noit_error, "AMQP connect: %s:%d\n", driver->hostname[sidx], driver->port); BUMPSTAT(connects); driver->hostidx = sidx; timeout.tv_sec = driver->heartbeat; timeout.tv_usec = 0; driver->sockfd = amqp_open_socket(driver->hostname[sidx], driver->port, &timeout); if(driver->sockfd < 0) { noitL(noit_error, "AMQP connect failed: %s:%d\n", driver->hostname[sidx], driver->port); return -1; } driver->has_error = 0; driver->connection = amqp_new_connection(); amqp_set_basic_return_cb(driver->connection, noit_rabbitmq_brcb, driver); amqp_set_sockfd(driver->connection, driver->sockfd); r = amqp_login(driver->connection, driver->vhost, 0, 131072, driver->heartbeat, AMQP_SASL_METHOD_PLAIN, driver->username, driver->password); if(r.reply_type != AMQP_RESPONSE_NORMAL) { noitL(noit_error, "AMQP login failed\n"); amqp_connection_close(driver->connection, AMQP_REPLY_SUCCESS); amqp_destroy_connection(driver->connection); driver->connection = NULL; return -1; } amqp_channel_open(driver->connection, 1); rptr = amqp_get_rpc_reply(); if(rptr->reply_type != AMQP_RESPONSE_NORMAL) { noitL(noit_error, "AMQP channe_open failed\n"); amqp_connection_close(driver->connection, AMQP_REPLY_SUCCESS); amqp_destroy_connection(driver->connection); driver->connection = NULL; return -1; } gettimeofday(&driver->last_hb, NULL); return 0; } /* 1 means already connected */ return 1; }
static void fq_logger(fq_client c, const char *err) { int i; mtevL(nlerr, "fq: %s\n", err); for(i=0;i<global_fq_ctx.nhosts;i++) { if(c == global_fq_ctx.client[i]) { BUMPSTAT(i, error_messages); /* We only care about this if we're using round robin processing */ if (global_fq_ctx.round_robin) { if (!strncmp(err, "socket: Connection refused", strlen("socket: Connection refused"))) { global_fq_ctx.down_host[i] = true; global_fq_ctx.last_error[i] = time(NULL); } } break; } } }
tbs_boolean_t mvfs_rddir_cache_get( struct mfs_mnode *mnp, struct uio *uiop, CRED_T *cred, int *eofp, int *errorp ) { register int i; struct mvfs_rce *ep; mvfs_common_data_t *mcdp = MDKI_COMMON_GET_DATAP(); int size; ASSERT(MFS_ISVOB(mnp)); ASSERT(MISLOCKED(mnp)); if (!mcdp->mvfs_rdcenabled) { return FALSE; } if (mnp->mn_vob.rddir_cache != NULL) { for (i = 0, ep = &mnp->mn_vob.rddir_cache->entries[0]; i < mnp->mn_vob.rddir_cache->nentries; i++, ep++) { /* if valid, at the right offset, and small enough, use it */ if (ep->valid && MVFS_UIO_OFFSET(uiop) == ep->offset && uiop->uio_resid >= ep->size) { MDB_XLOG((MDB_MNOPS, "rddir cache hit mnp %"MVFS_FMT_UIO_OFFSET_X " off %"MVFS_FMT_MOFFSET_T_X" size %lx\n", mnp, MVFS_UIO_OFFSET(uiop), ep->size)); if (ep->size) { /* We put the size on the stack instead of using it * directly because the linux readdir_uiomove will 0 * the size value passed in on a buffer overflow so * that we don't skip entries. So we need a temp * value so that the readdir cache is not trashed. */ size = ep->size; *errorp = READDIR_UIOMOVE(ep->block, &size, UIO_READ, uiop, ep->offset); if (!READDIR_BUF_FULL(uiop)) { /* Should we advance offset if there was * an error? The previous code did this * unconditionally (before addition of * READDIR_BUF_FULL() macro). */ MVFS_UIO_OFFSET(uiop) = ep->endoffset; } } else { *errorp = 0; } if (eofp != NULL) { *eofp = ep->eof; } BUMPSTAT(mfs_acstat.ac_rddirhit); return TRUE; } } } else { MDB_XLOG((MDB_MNOPS, "rddir cache get (empty) mnp %lx\n", mnp)); } BUMPSTAT(mfs_acstat.ac_rddirmiss); MDB_XLOG((MDB_MNOPS, "rddir cache miss mnp %lx off %"MVFS_FMT_UIO_OFFSET_X " size %"MVFS_FMT_UIO_RESID_X"\n", mnp, MVFS_UIO_OFFSET(uiop), uiop->uio_resid)); return FALSE; }
static void noit_rabbitmq_brcb(amqp_channel_t channel, amqp_basic_return_t *m, void *closure) { BUMPSTAT(basic_returns); mtevL(mtev_debug, "AMQP return [%d:%.*s]\n", m->reply_code, (int)m->reply_text.len, (char *)m->reply_text.bytes); }
static int noit_fq_submit(iep_thread_driver_t *dr, const char *payload, size_t payloadlen) { int i; struct fq_driver *driver = (struct fq_driver *)dr; const char *routingkey = driver->routingkey; mtev_hash_table *filtered_metrics; char uuid_formatted_str[UUID_STR_LEN+1]; bool is_bundle = false, is_metric = false, send = false; fq_msg *msg; char *metric = NULL; if(*payload == 'M' || *payload == 'S' || *payload == 'C' || (*payload == 'H' && payload[1] == '1') || (*payload == 'F' && payload[1] == '1') || (*payload == 'B' && (payload[1] == '1' || payload[1] == '2'))) { char uuid_str[32 * 2 + 1]; int account_id, check_id; if (*payload == 'B') is_bundle = true; else if ((*payload == 'H') || (*payload == 'M')) { is_metric = true; } if(extract_uuid_from_jlog(payload, payloadlen, &account_id, &check_id, uuid_str, uuid_formatted_str, &metric)) { if(*routingkey) { char *replace; int newlen = strlen(driver->routingkey) + 1 + sizeof(uuid_str) + 2 * 32; replace = alloca(newlen); snprintf(replace, newlen, "%s.%x.%x.%d.%d%s", driver->routingkey, account_id%16, (account_id/16)%16, account_id, check_id, uuid_str); routingkey = replace; } } } /* Let through any messages that aren't metrics or bundles */ if (!is_bundle && !is_metric) { send = true; } /* Setup our message */ msg = fq_msg_alloc(payload, payloadlen); if(msg == NULL) { driver->allocation_failures++; if (metric) free(metric); return -1; } driver->msg_cnt++; fq_msg_exchange(msg, driver->exchange, strlen(driver->exchange)); mtevL(mtev_debug, "route[%s] -> %s\n", driver->exchange, routingkey); fq_msg_route(msg, routingkey, strlen(routingkey)); fq_msg_id(msg, NULL); if (global_fq_ctx.round_robin) { int checked = 0, good = 0; time_t cur_time; while (1) { if (!global_fq_ctx.down_host[global_fq_ctx.round_robin_target]) { good = 1; break; } cur_time = time(NULL); if (cur_time - global_fq_ctx.last_error[global_fq_ctx.round_robin_target] >= 10) { global_fq_ctx.down_host[global_fq_ctx.round_robin_target] = false; good = 1; break; } global_fq_ctx.round_robin_target = (global_fq_ctx.round_robin_target+1) % driver->nhosts; checked++; if (checked == driver->nhosts) { /* This means everybody is down.... just try to send to whatever fq we're pointing at */ break; } } if (good) { if(fq_client_publish(driver->client[global_fq_ctx.round_robin_target], msg) == 1) { BUMPSTAT(global_fq_ctx.round_robin_target, publications); } else { BUMPSTAT(global_fq_ctx.round_robin_target, client_tx_drop); } } /* Go ahead and try to publish to the hosts that are down, just in case they've come back up. This should help minimize lost messages */ for (i=0; i<driver->nhosts; i++) { if (global_fq_ctx.down_host[i]) { if(fq_client_publish(driver->client[i], msg) == 1) { BUMPSTAT(i, publications); } else { BUMPSTAT(i, client_tx_drop); } } } global_fq_ctx.round_robin_target = (global_fq_ctx.round_robin_target+1) % driver->nhosts; } else { for(i=0; i<driver->nhosts; i++) { if(fq_client_publish(driver->client[i], msg) == 1) { BUMPSTAT(i, publications); } else { BUMPSTAT(i, client_tx_drop); } } } fq_msg_deref(msg); if (!send) { if(mtev_hash_retrieve(&filtered_checks_hash, uuid_formatted_str, strlen(uuid_formatted_str), (void**)&filtered_metrics)) { if (is_bundle || (is_metric && mtev_hash_size(filtered_metrics) == 0)) { send = true; } else if (is_metric) { void *tmp; if (mtev_hash_retrieve(filtered_metrics, metric, strlen(metric), &tmp)) { send = true; } } } } if (global_fq_ctx.filtered_exchange[0] && send) { fq_msg *msg2; msg2 = fq_msg_alloc(payload, payloadlen); fq_msg_exchange(msg2, driver->filtered_exchange, strlen(driver->filtered_exchange)); mtevL(mtev_debug, "route[%s] -> %s\n", driver->filtered_exchange, routingkey); fq_msg_route(msg2, routingkey, strlen(routingkey)); fq_msg_id(msg2, NULL); for(i=0; i<driver->nhosts; i++) { if(fq_client_publish(driver->client[i], msg2) == 1) { BUMPSTAT(i, publications); } else { BUMPSTAT(i, client_tx_drop); } } fq_msg_deref(msg2); } if (metric) free(metric); return 0; }