bool zk::set(const string& path, const string& payload) { scoped_lock lk(m_); int rc = zoo_set(zh_, path.c_str(), payload.c_str(), payload.length(), -1); if (rc != ZOK) { LOG(ERROR) << path << " failed in setting " << rc << " " << zerror(rc); return false; } DLOG(INFO) << __func__ << " " << path << " - " << payload; return true; }
/** * Callback with the list of children. If the local announcement is not present, create an ephemeral node on zk. */ static void node_completion(int rc, const struct String_vector *strings, const void *data) { if (rc) { LOG_WARN(("Error %s while retrieving children!", zerror(rc))); return; } unsigned long tick = *((unsigned long *)data); LOG_DEBUG(("Callback Tick (%d/%lx)", tick)); if (!strings) { return; } for (int i = 0; i < strings->count; i++) { if (!strcmp(strings->data[i], announce_name)) { LOG_DEBUG(("Found local announcement %s", announce_name)); return; } } // Need to add local announcement. LOG_DEBUG(("Local announcement not found, creating %s", announce_path)); int rc2 = zoo_acreate(zh, announce_path, announce_data, strlen(announce_data), &ZOO_OPEN_ACL_UNSAFE, ZOO_EPHEMERAL, void_completion, NULL); if (rc2) { LOG_WARN(("Error %s while creating announcement!", zerror(rc))); } }
char * platform_read_entire_file(const char *path, Memory_Arena *ma) { int fd = open(path, O_RDONLY); if (fd < 0) { zerror("could not load file %s", path); return NULL; } off_t len = lseek(fd, 0, SEEK_END); if (len < 0) { zerror("could not get %s file length. %s.\n", path, perrno()); return NULL; } lseek(fd, 0, SEEK_SET); char *buf = mem_alloc_array(char, (len+1), ma); // read may return less bytes than requested, so we have to loop. off_t tot_read = 0, cur_read = 0; char *pos = buf; do { cur_read = read(fd, pos, (len - tot_read)); tot_read += cur_read; pos += cur_read; } while (tot_read < len && cur_read != 0); if (tot_read != len) { zerror("could not read file %s.", path, perrno()); return NULL; } buf[len] = '\0'; close(fd); return buf; }
void create_log_thread(zlog_t *logp, zoneid_t id) { int res; zlog_mode_t mode; shutting_down = 0; zlogp = logp; mode = get_logger_mode(); if (mode == ZLOG_NONE) return; if (init_zfd_devs(zlogp, mode) == -1) { zerror(zlogp, B_FALSE, "zfd setup: device initialization failed"); return; } res = thr_create(NULL, 0, (void * (*)(void *))srvr, (void *)mode, 0, &logger_tid); if (res != 0) { zerror(zlogp, B_FALSE, "error %d creating logger thread", res); logger_tid = 0; } }
static int destroy_console_devs(zlog_t *zlogp) { char conspath[MAXPATHLEN]; di_node_t root; struct cb_data cb; int masterfd; int slavefd; /* * Signal the master side to release its handle on the slave side by * issuing a ZC_RELEASESLAVE ioctl. */ (void) snprintf(conspath, sizeof (conspath), "/dev/zcons/%s/%s", zone_name, ZCONS_MASTER_NAME); if ((masterfd = open(conspath, O_RDWR | O_NOCTTY)) != -1) { (void) snprintf(conspath, sizeof (conspath), "/dev/zcons/%s/%s", zone_name, ZCONS_SLAVE_NAME); if ((slavefd = open(conspath, O_RDWR | O_NOCTTY)) != -1) { if (ioctl(masterfd, ZC_RELEASESLAVE, (caddr_t)(intptr_t)slavefd) != 0) zerror(zlogp, B_TRUE, "WARNING: error while " "releasing slave handle of zone console for" " %s", zone_name); (void) close(slavefd); } else { zerror(zlogp, B_TRUE, "WARNING: could not open slave " "side of zone console for %s to release slave " "handle", zone_name); } (void) close(masterfd); } else { zerror(zlogp, B_TRUE, "WARNING: could not open master side of " "zone console for %s to release slave handle", zone_name); } bzero(&cb, sizeof (cb)); cb.zlogp = zlogp; if ((root = di_init(ZCONSNEX_DEVTREEPATH, DINFOCPYALL)) == DI_NODE_NIL) { zerror(zlogp, B_TRUE, "%s failed", "di_init"); return (-1); } (void) di_walk_node(root, DI_WALK_CLDFIRST, (void *)&cb, destroy_cb); if (cb.found > 1) { zerror(zlogp, B_FALSE, "WARNING: multiple zone console " "instances detected for zone '%s'; %d of %d " "successfully removed.", zone_name, cb.killed, cb.found); } di_fini(root); return (0); }
/** * create node in zookeeper server * \param node indicate key * param flag =ZOO_EPHEMERAL */ bool ZKOP::zkCreateNodePath(const std::string& node, int flag) {/*{{{*/ int rc = 0; /* if ((rc = zoo_exists(zkhandle, node.data(), 0, NULL)) == ZOK) { return true; } if (rc != ZNONODE) { //LOG(ERROR) << "create new node failed, node = [" << node << "], error = [" << zerror(rc) << "]"; return false; } if (zoo_exists(zkhandle, node.data(), 0, NULL) == ZNONODE) { if ((rc = zoo_create(zkhandle, node.data(), NULL, -1, &ZOO_OPEN_ACL_UNSAFE, flag, NULL, 0)) != ZOK) { LOG(ERROR) << "create new node failed, node = [" << node << "], error = [" << zerror(rc) << "]"; return false; } } LOG(INFO) << "create new node successful, node = [" << node << "], flag = [" << flag << "]"; return true; */ rc = zkNodeExists(node, flag); if( ZOK == rc ) { return true; } if(ZNONODE != rc){ return false; } if(ZNONODE == rc){ if ((rc = zoo_create(zkhandle, node.data(), NULL, -1, &ZOO_OPEN_ACL_UNSAFE, flag, NULL, 0)) != ZOK) { LOG(ERROR) << "create new node failed, node = [" << node << "], error = [" << zerror(rc) << "]"; return false; } }else{ std::stringstream ss; std::string str; ss << rc; ss >> str; LOG(ERROR) << "create new node failed, node = [" << node << "], error = [" << zerror(rc) << "]" << "\trc=" << str; return false; } return true; }/*}}}*/
int init_console(zlog_t *zlogp) { if (init_console_dev(zlogp) == -1) { zerror(zlogp, B_FALSE, "console setup: device initialization failed"); } if ((serverfd = init_console_sock(zlogp)) == -1) { zerror(zlogp, B_FALSE, "console setup: socket initialization failed"); return (-1); } return (0); }
vector<BackendItem> MasterHandler::getExistingAssignments() { vector<BackendItem> result; if (ZooHandler::getInstance().sessionState != ZOO_CONNECTED_STATE) { LOG(ERROR)<<"Invalid sessionstate"; return result; } //1)get list of (assignmentznode)/BFSElection children and set a watch for changes in these folder String_vector children; int callResult = zoo_get_children(ZooHandler::getInstance().zh, ZooHandler::getInstance().assignmentZNode.c_str(),0, &children); if (callResult != ZOK) { LOG(ERROR)<<"zoo_get_children failed:"<<zerror(callResult); return result; } //2)get content of each node for (int i = 0; i < children.count; i++) { string node(children.data[i]); //Allocate 1MB data const int length = 1024 * 1024; char *buffer = new char[length]; int len = length; int callResult = zoo_get(ZooHandler::getInstance().zh, (ZooHandler::getInstance().assignmentZNode + "/" + node).c_str(), 0, buffer, &len, nullptr); if (callResult != ZOK) { LOG(ERROR)<<"zoo_get failed:"<<zerror(callResult); delete[] buffer; buffer = nullptr; continue; } if(len >= 0 && len <= length-1) buffer[len] = '\0'; //3)parse node content to a znode char *tok = strtok(buffer, "\n"); while (tok != NULL) { string file(tok); result.push_back(BackendItem(file,-1l,"","")); tok = strtok(NULL, "\n"); } //Release memory delete[] buffer; buffer = nullptr; } return result; }
void zk::remove(const std::string& path) { scoped_lock lk(m_); int rc = zoo_delete(zh_, path.c_str(), -1); if(rc != ZOK and rc != ZNONODE) { LOG(ERROR) << path << ": removal failed - " << zerror(rc); } };
bool ZKOP::zkGetNodeData(const std::string& node, std::string& data, int size, int watch) {/*{{{*/ data.resize(size); int rc = 0; if ((rc = zoo_get(zkhandle, node.data(), watch, &data[0], &size, NULL)) != ZOK) { LOG(ERROR) << "get node data failed, node = [" << node << "], error = [" << zerror(rc) << "]" << std::endl; return false; } do { if (size < 0) { data.resize(0); break; } data.resize(size); } while (0); /* #ifndef NDEBUG LOG(INFO) << "get node data successful, node = [" << node << "], data = [" << data << "], size = [" << size << "]" << std::endl; #endif */ return true; }/*}}}*/
static MinixInode *search_dir(MinixInode *di,String name){ if(isNullp(di)) return NULL; static char block[BLOCK_SIZE]; MinixDirentry *drp = (MinixDirentry *)block; MinixInode *inode = malloc(sizeof(MinixInode)); if(inode == NULL) goto error_ret; zone_t dnoze = FULL_BLOCK(di->i_size); for(int i = 0;i < dnoze;i++){ if(ERROR == zone_rw(di,READ,i,block)){ zerror("search_dir : zone_rw fail"); goto error_ret; } for(int j = 0;j < DIR_IN_BLOCK;j++){ if(_isEqName(name,drp[j].name)){ if(ERROR == get_inode(drp[j].inode,inode)) goto error_ret; return inode; } } } error_ret: if(inode) free(inode); return NULL; }
/** * periodically called by the main memcache loop. This will connect zookeeper if * necessary. Also, if the generation has changed (because of a zookeeper even), * it will then trigger data processing. */ void mc_zookeeper_tick() { ticker++; if (!zh) { LOG_DEBUG(("Connecting zookeeper...")); zh = zookeeper_init(settings.zookeeper_connect, process, 30000, &myid, 0, 0); if (!zh) { LOG_INFO(("Could not connect to zookeeper, error: %d", errno)); } else { LOG_DEBUG(("Zookeeper connection ok, status is %d", zoo_state(zh))); } trigger_event(); } if (connected) { long current_generation = generation; if (last_generation < current_generation) { LOG_DEBUG(("Tick (%d)", ticker)); int rc = zoo_aget_children(zh, settings.zookeeper_path, 1, node_completion, &ticker); if (rc != 0) { LOG_WARN(("Error %s while retrieving children!", zerror(rc))); } else { last_generation = current_generation; } } } }
/** * Callback for the node creation. */ static void void_completion(int rc, const char *name, const void *data) { if (rc) { LOG_WARN(("Error %s while creating announcement!", zerror(rc))); } else { LOG_DEBUG(("Node creation complete, service now announced!")); } }
/* * Given a pointer returned by zmalloc or zcalloc, free it and * return a pointer to a new size, basically acting like realloc(). * Requires: ptr was returned by zmalloc, zcalloc, or zrealloc with the * same type. * Effects: Returns a pointer to the new memory, or aborts. */ void * zrealloc (int type, void *ptr, size_t size) { void *memory; memory = realloc (ptr, size); if (memory == NULL) zerror ("realloc", type, size); return memory; }
bool zk::remove(const string& path) { scoped_lock lk(m_); int rc = zoo_delete(zh_, path.c_str(), -1); if (rc != ZOK && rc != ZNONODE) { LOG(ERROR) << "failed to remove: " << path << " - " << zerror(rc); return false; } DLOG(INFO) << __func__ << " " << path; return true; }
void zk::create(const std::string& path, const std::string& payload, bool ephemeral) { scoped_lock lk(m_); int rc = zoo_create(zh_, path.c_str(), payload.c_str(), payload.length(), &ZOO_OPEN_ACL_UNSAFE, ((ephemeral)?ZOO_EPHEMERAL:0), // | ZOO_SEQUENCE NULL, 0); if(ephemeral) { if(rc != ZOK) { LOG(ERROR) << path << " failed in creation:" << zerror(rc); throw JUBATUS_EXCEPTION(jubatus::exception::runtime_error("failed to create zk empheral node") << jubatus::exception::error_message(std::string("zerror: ") + zerror(rc)) << jubatus::exception::error_api_func("zoo_create") << jubatus::exception::error_file_name(path)); } } else { if(rc != ZOK && rc != ZNODEEXISTS) { LOG(ERROR) << path << " failed in creation " << rc << " " << zerror(rc); } } };
/* * Duplicate a string, counting memory usage by type. * Effects: The string is duplicated, and the return value must * eventually be passed to zfree with the same type. The function will * succeed or abort. */ char * zstrdup (int type, const char *str) { void *dup; dup = strdup (str); if (dup == NULL) zerror ("strdup", type, strlen (str)); alloc_inc (type); return dup; }
void zk::list_(const std::string& path, std::vector<std::string>& out) { struct String_vector s; int rc = zoo_get_children(zh_, path.c_str(), 0, &s); if(rc == ZOK) { for(int i=0; i<s.count; ++i) { out.push_back(s.data[i]); // full path => #{path}/#{s.data[i]} } std::sort(out.begin(), out.end()); } else { LOG(ERROR) << zerror(rc) << " (" << path << ")"; } };
/* Memory reallocation. */ void * zrealloc (int type, void *ptr, size_t size) { void *memory; memory = realloc (ptr, size); #ifdef BRCM_RIP_DEBUG if (memory == NULL) zerror ("realloc", type, size); #endif return memory; }
bool zk::create(const string& path, const string& payload, bool ephemeral) { scoped_lock lk(m_); int rc = zoo_create(zh_, path.c_str(), payload.c_str(), payload.length(), &ZOO_OPEN_ACL_UNSAFE, ((ephemeral) ? ZOO_EPHEMERAL : 0), // | ZOO_SEQUENCE NULL, 0); if (ephemeral) { if (rc != ZOK) { LOG(ERROR) << "failed to create: " << path << " - " << zerror(rc); return false; } } else { if (rc != ZOK && rc != ZNODEEXISTS) { LOG(ERROR) << "failed to create: " << path << " - " << zerror(rc); return false; } } DLOG(INFO) << __func__ << " " << path; return true; }
// TODO: Handle modes. File_Handle platform_open_file(const char *path, const char *mode) { File_Handle fh; fh.descriptor = open(path, O_RDONLY); if (fh.descriptor < 0) { zerror("could not open file %s\n", path); fh.descriptor = -1; return fh; } return fh; }
// "/some/path" => "/some/path0000012" void zk::create_seq(const std::string& path, std::string& seqfile) { scoped_lock lk(m_); char path_buffer[path.size()+16]; int rc = zoo_create(zh_, path.c_str(), NULL, 0, &ZOO_OPEN_ACL_UNSAFE, ZOO_EPHEMERAL|ZOO_SEQUENCE, path_buffer, path.size()+16); seqfile = ""; if(rc != ZOK) { LOG(ERROR) << path << " failed in creation - " << zerror(rc); } else { seqfile = path_buffer; } };
bool zk::hd_list(const string& path, string& out) { struct String_vector s; scoped_lock lk(m_); int rc = zoo_get_children(zh_, path.c_str(), 0, &s); if (rc == ZOK) { if (0 < s.count) { out = s.data[0]; } return true; } LOG(ERROR) << "failed to get children: " << path << " - " << zerror(rc); return false; }
bool zk::read(const string& path, string& out) { scoped_lock lk(m_); char buf[1024]; int buflen = 1024; int rc = zoo_get(zh_, path.c_str(), 0, buf, &buflen, NULL); if (rc == ZOK) { out = string(buf, buflen); return buflen <= 1024; } else { LOG(ERROR) << "failed to get data: " << path << " - " << zerror(rc); return false; } }
/* Memory allocation. */ void * zmalloc (int type, size_t size) { void *memory; memory = malloc (size); #ifdef BRCM_RIP_DEBUG if (memory == NULL) zerror ("malloc", type, size); alloc_inc (type); #endif return memory; }
/* String duplication. */ char * zstrdup (int type, char *str) { void *dup; dup = strdup (str); #ifdef BRCM_RIP_DEBUG if (dup == NULL) zerror ("strdup", type, strlen (str)); alloc_inc (type); #endif return dup; }
void platform_read(File_Handle fh, size_t read_nbytes, void *buf) { off_t tot_read = 0, cur_read = 0; char *pos = (char *)buf; do { cur_read = read(fh.descriptor, pos, (read_nbytes - tot_read)); tot_read += cur_read; pos += cur_read; } while (tot_read < read_nbytes && cur_read != 0); if (tot_read != read_nbytes) zerror("could not read from file %s.", perrno()); }
static int open_fd(zlog_t *zlogp, int id, int rw) { int fd; int flag = O_NONBLOCK | O_NOCTTY | O_CLOEXEC; int retried = 0; char stdpath[MAXPATHLEN]; (void) snprintf(stdpath, sizeof (stdpath), "/dev/zfd/%s/master/%d", zone_name, id); flag |= rw; while (!shutting_down) { if ((fd = open(stdpath, flag)) != -1) { /* * Setting RPROTDIS on the stream means that the * control portion of messages received (which we don't * care about) will be discarded by the stream head. If * we allowed such messages, we wouldn't be able to use * read(2), as it fails (EBADMSG) when a message with a * control element is received. */ if (ioctl(fd, I_SRDOPT, RNORM|RPROTDIS) == -1) { zerror(zlogp, B_TRUE, "failed to set options on zfd"); return (-1); } return (fd); } if (retried++ > 60) break; (void) sleep(1); } zerror(zlogp, B_TRUE, "failed to open zfd"); return (-1); }
static int init_server_sock(zlog_t *zlogp, int *servfd, char *nm) { int resfd = -1; struct sockaddr_un servaddr; bzero(&servaddr, sizeof (servaddr)); servaddr.sun_family = AF_UNIX; (void) snprintf(servaddr.sun_path, sizeof (servaddr.sun_path), SERVER_SOCKPATH, zone_name, nm); if ((resfd = socket(AF_UNIX, SOCK_STREAM, 0)) == -1) { zerror(zlogp, B_TRUE, "server setup: could not create socket"); goto err; } (void) unlink(servaddr.sun_path); if (bind(resfd, (struct sockaddr *)&servaddr, sizeof (servaddr)) == -1) { zerror(zlogp, B_TRUE, "server setup: could not bind to socket"); goto err; } if (listen(resfd, 4) == -1) { zerror(zlogp, B_TRUE, "server setup: could not listen on socket"); goto err; } *servfd = resfd; return (0); err: (void) unlink(servaddr.sun_path); if (resfd != -1) (void) close(resfd); return (-1); }
/* * destroy_zfd_devs() and its helper destroy_cb() tears down any zfd instances * associated with this zone. If things went very wrong, we might have an * incorrect number of instances hanging around. This routine hunts down and * tries to remove all of them. Of course, if the fd is open, the instance will * not detach, which is a potential issue. */ static int destroy_cb(di_node_t node, void *arg) { struct cb_data *cb = (struct cb_data *)arg; char *prop_data; char *tmp; char devpath[MAXPATHLEN]; devctl_hdl_t hdl; if (di_prop_lookup_strings(DDI_DEV_T_ANY, node, "zfd_zname", &prop_data) == -1) return (DI_WALK_CONTINUE); assert(prop_data != NULL); if (strcmp(prop_data, zone_name) != 0) { /* this is a zfd for a different zone */ return (DI_WALK_CONTINUE); } cb->found++; tmp = di_devfs_path(node); (void) snprintf(devpath, sizeof (devpath), "/devices/%s", tmp); di_devfs_path_free(tmp); if ((hdl = devctl_device_acquire(devpath, 0)) == NULL) { zerror(cb->zlogp, B_TRUE, "WARNING: zfd %s found, " "but it could not be controlled.", devpath); return (DI_WALK_CONTINUE); } if (devctl_device_remove(hdl) == 0) { cb->killed++; } else { zerror(cb->zlogp, B_TRUE, "WARNING: zfd %s found, " "but it could not be removed.", devpath); } devctl_release(hdl); return (DI_WALK_CONTINUE); }