コード例 #1
0
/*
 * delete a given job log directory
 * This function takes jobid and deletes the related logs.
 */
int delete_log_directory(const char *subdir, const char * good_local_dirs) {
  char* job_log_dir = get_job_log_directory(subdir);
  
  int ret = -1;
  if (job_log_dir == NULL) return ret;

  //delete the job log directory in <hadoop.log.dir>/userlogs/jobid
  delete_path(job_log_dir, true);

  char **local_dir = get_mapred_local_dirs(good_local_dirs);

  char **local_dir_ptr;
  for(local_dir_ptr = local_dir; *local_dir_ptr != NULL; ++local_dir_ptr) {
     char *mapred_local_log_dir = concatenate("%s/userlogs/%s", 
				      "mapred local job log dir", 
			      	      2, *local_dir_ptr, subdir);
     if (mapred_local_log_dir != NULL) {
        //delete the job log directory in <mapred.local.dir>/userlogs/jobid
        delete_path(mapred_local_log_dir, true);
	free(mapred_local_log_dir);
     }
     else
        fprintf(LOGFILE, "Failed to delete mapred local log dir for jobid %s\n",
            subdir);
  }
  free(job_log_dir);
  free_values(local_dir);
  return 0;
}
コード例 #2
0
/**
 * Delete the given directory as the user from each of the directories
 * user: the user doing the delete
 * subdir: the subdir to delete (if baseDirs is empty, this is treated as
           an absolute path)
 * baseDirs: (optional) the baseDirs where the subdir is located
 */
int delete_as_user(const char *user,
                   const char *subdir,
                   char* const* baseDirs) {
  int ret = 0;

  char** ptr;

  // TODO: No switching user? !!!!
  if (baseDirs == NULL || *baseDirs == NULL) {
    return delete_path(subdir, strlen(subdir) == 0);
  }
  // do the delete
  for(ptr = (char**)baseDirs; *ptr != NULL; ++ptr) {
    char* full_path = concatenate("%s/%s", "user subdir", 2,
                              *ptr, subdir);
    if (full_path == NULL) {
      return -1;
    }
    int this_ret = delete_path(full_path, strlen(subdir) == 0);
    free(full_path);
    // delete as much as we can, but remember the error
    if (this_ret != 0) {
      ret = this_ret;
    }
  }
  return ret;
}
コード例 #3
0
ファイル: vc-utils.c プロジェクト: Guilhem30/seafile
static int
delete_dir_recursive (const char *repo_id,
                      int repo_version,
                      const char *dir_path,
                      SeafDir *dir,
                      const char *worktree,
                      struct index_state *istate)
{
    GList *ptr;
    SeafDirent *dent;
    char *sub_path;
    SeafDir *sub_dir;

    for (ptr = dir->entries; ptr; ptr = ptr->next) {
        dent = ptr->data;
        sub_path = g_strconcat (dir_path, "/", dent->name, NULL);

        if (S_ISDIR(dent->mode)) {
            if (strcmp(dent->id, EMPTY_SHA1) == 0) {
                delete_path (worktree, sub_path, dent->mode, 0);
            } else {
                sub_dir = seaf_fs_manager_get_seafdir (seaf->fs_mgr,
                                                       repo_id, repo_version,
                                                       dent->id);
                if (!sub_dir) {
                    seaf_warning ("Failed to find dir %s in repo %.8s.\n",
                                  sub_path, repo_id);
                    g_free (sub_path);
                    return -1;
                }

                if (delete_dir_recursive (repo_id, repo_version,
                                          sub_path, sub_dir,
                                          worktree, istate) < 0) {
                    g_free (sub_path);
                    return -1;
                }

                seaf_dir_free (sub_dir);
            }
        } else if (S_ISREG(dent->mode)) {
            struct cache_entry *ce;

            ce = index_name_exists (istate, sub_path, strlen(sub_path), 0);
            if (ce) {
                delete_path (worktree, sub_path, dent->mode, ce->ce_mtime.sec);
            }
        }

        g_free (sub_path);
    }

    char *full_path = g_build_filename (worktree, dir_path, NULL);
    if (seaf_remove_empty_dir (full_path) < 0) {
        seaf_warning ("Failed to remove dir %s: %s.\n", full_path, strerror(errno));
        return -1;
    }

    return 0;
}
コード例 #4
0
/**
 * Delete the given directory as the user from each of the tt_root directories
 * user: the user doing the delete
 * subdir: the subdir to delete
 */
int delete_as_user(const char *user, const char * good_local_dirs,
                   const char *subdir) {
  int ret = 0;

  char** tt_roots = get_mapred_local_dirs(good_local_dirs);
  char** ptr;
  if (tt_roots == NULL || *tt_roots == NULL) {
    fprintf(LOGFILE, "Good mapred local directories could ot be obtained.\n");
    return INVALID_TT_ROOT;
  }

  // do the delete
  for(ptr = tt_roots; *ptr != NULL; ++ptr) {
    char* full_path = get_user_subdirectory(*ptr, user, subdir);
    if (full_path == NULL) {
      return -1;
    }
    int this_ret = delete_path(full_path, strlen(subdir) == 0);
    free(full_path);
    // delete as much as we can, but remember the error
    if (this_ret != 0) {
      ret = this_ret;
    }
  }
  free_values(tt_roots);
  return ret;
}
コード例 #5
0
static void
make_path( sliceable_switch *sliceable_switch, uint64_t in_datapath_id, uint16_t in_port, uint16_t in_vid,
           uint64_t out_datapath_id, uint16_t out_port, uint16_t out_vid, const buffer *packet ) {
  dlist_element *hops = resolve_path( sliceable_switch->pathresolver, in_datapath_id, in_port, out_datapath_id, out_port );
  if ( hops == NULL ) {
    warn( "No available path found ( %#" PRIx64 ":%u -> %#" PRIx64 ":%u ).",
          in_datapath_id, in_port, out_datapath_id, out_port );
    discard_packet_in( in_datapath_id, in_port, packet );
    return;
  }

  // check if the packet is ARP or not
  if ( sliceable_switch->handle_arp_with_packetout && packet_type_arp( packet ) ) {
    // send packet out for tail switch
    free_hop_list( hops );
    output_packet( packet, out_datapath_id, out_port, out_vid );
    return;
  }

  const uint32_t wildcards = 0;
  struct ofp_match match;
  set_match_from_packet( &match, in_port, wildcards, packet );

  if ( lookup_path( in_datapath_id, match, PRIORITY ) != NULL ) {
    warn( "Duplicated path found." );
    output_packet( packet, out_datapath_id, out_port, out_vid );
    return;
  }

  const uint16_t hard_timeout = 0;
  path *p = create_path( match, PRIORITY, sliceable_switch->idle_timeout, hard_timeout );
  assert( p != NULL );
  for ( dlist_element *e = get_first_element( hops ); e != NULL; e = e->next ) {
    pathresolver_hop *rh = e->data;
    hop *h = create_hop( rh->dpid, rh->in_port_no, rh->out_port_no, NULL );
    assert( h != NULL );
    append_hop_to_path( p, h );
  } // for(;;)

  dlist_element *e = get_last_element( hops );
  pathresolver_hop *last_hop = e->data;
  packet_out_params *params = xmalloc( sizeof( struct packet_out_params ) );
  params->packet = duplicate_buffer( packet );
  params->out_datapath_id = last_hop->dpid;
  params->out_port_no = last_hop->out_port_no;
  params->out_vid = out_vid;

  bool ret = setup_path( p, handle_setup, params, NULL, NULL );
  if ( ret != true ) {
    error( "Failed to set up path." );
    output_packet( packet, out_datapath_id, out_port, out_vid );
    free_buffer( params->packet );
    xfree( params );
  }

  delete_path( p );

  // free them
  free_hop_list( hops );
}
コード例 #6
0
ファイル: task-controller.c プロジェクト: InMobi/hadoop
/**
 * Delete the given directory as the user from each of the tt_root directories
 * user: the user doing the delete
 * subdir: the subdir to delete
 */
int delete_as_user(const char *user,
                   const char *subdir) {
  int ret = 0;

  char** tt_roots = get_values(TT_SYS_DIR_KEY);
  char** ptr;
  if (tt_roots == NULL || *tt_roots == NULL) {
    fprintf(LOGFILE, "No %s defined in the configuration\n", TT_SYS_DIR_KEY);
    return INVALID_CONFIG_FILE;
  }

  // do the delete
  for(ptr = tt_roots; *ptr != NULL; ++ptr) {
    char* full_path = get_user_subdirectory(*ptr, user, subdir);
    if (full_path == NULL) {
      return -1;
    }
    int this_ret = delete_path(full_path, strlen(subdir) == 0);
    free(full_path);
    // delete as much as we can, but remember the error
    if (this_ret != 0) {
      ret = this_ret;
    }
  }
  free_values(tt_roots);
  return ret;
}
コード例 #7
0
ファイル: flipPath.cpp プロジェクト: yugiohatemu/Code-C
FlipPath::~FlipPath(){
    //Avoid deleteing next multiple time
    for (int i = 0; i < next_path.size();i++) {
        if (next != next_path[i]) {
            delete_path(next_path[i]);
        }
    }
}
コード例 #8
0
ファイル: task-controller.c プロジェクト: InMobi/hadoop
/**
 * delete a given log directory
 */
int delete_log_directory(const char *subdir) {
  char* log_subdir = get_job_log_directory(subdir);
  int ret = -1;
  if (log_subdir != NULL) {
    ret = delete_path(log_subdir, strchr(subdir, '/') == NULL);
  }
  free(log_subdir);
  return ret;
}
コード例 #9
0
int Lua_Monster_Move_By_Path(lua_State *L)
{
    int monster_index = Lua_Monster::Index(L, 1);
    int polygon_index = 0;
    if (lua_isnumber(L, 2))
    {
        polygon_index = static_cast<int>(lua_tonumber(L, 2));
        if (!Lua_Polygon::Valid(polygon_index))
            return luaL_error(L, "move_by_path: invalid polygon index");
    }
    else if (Lua_Polygon::Is(L, 2))
    {
        polygon_index = Lua_Polygon::Index(L, 2);
    }
    else
        return luaL_error(L, "move_by_path: incorrect argument type");

    monster_data *monster = get_monster_data(monster_index);
    if (MONSTER_IS_PLAYER(monster))
        return luaL_error(L, "move_by_path: monster is player");

    monster_definition *definition = get_monster_definition_external(monster->type);
    object_data *object = get_object_data(monster->object_index);
    monster_pathfinding_data path;
    world_point2d destination;

    if (!MONSTER_IS_ACTIVE(monster))
        activate_monster(monster_index);

    if (monster->path != NONE)
    {
        delete_path(monster->path);
        monster->path = NONE;
    }

    SET_MONSTER_NEEDS_PATH_STATUS(monster, false);
    path.definition = definition;
    path.monster = monster;
    path.cross_zone_boundaries = true;

    destination = get_polygon_data(polygon_index)->center;

    monster->path = new_path((world_point2d *) &object->location, object->polygon, &destination, polygon_index, 3 * definition->radius, monster_pathfinding_cost_function, &path);
    if (monster->path == NONE)
    {
        if (monster->action != _monster_is_being_hit || MONSTER_IS_DYING(monster))
        {
            set_monster_action(monster_index, _monster_is_stationary);
        }
        set_monster_mode(monster_index, _monster_unlocked, NONE);
        return 0;
    }

    advance_monster_path(monster_index);
    return 0;
}
コード例 #10
0
ファイル: container-executor.c プロジェクト: EddiePi/yarn-cpu
/**
 * Delete the given directory as the user from each of the directories
 * user: the user doing the delete
 * subdir: the subdir to delete (if baseDirs is empty, this is treated as
           an absolute path)
 * baseDirs: (optional) the baseDirs where the subdir is located
 */
int delete_as_user(const char *user,
                   const char *subdir,
                   char* const* baseDirs) {
  int ret = 0;
  int subDirEmptyStr = (subdir == NULL || subdir[0] == 0);
  int needs_tt_user = subDirEmptyStr;
  char** ptr;

  // TODO: No switching user? !!!!
  if (baseDirs == NULL || *baseDirs == NULL) {
    return delete_path(subdir, needs_tt_user);
  }
  // do the delete
  for(ptr = (char**)baseDirs; *ptr != NULL; ++ptr) {
    char* full_path = NULL;
    struct stat sb;
    if (stat(*ptr, &sb) != 0) {
      fprintf(LOGFILE, "Could not stat %s\n", *ptr);
      return -1;
    }
    if (!S_ISDIR(sb.st_mode)) {
      if (!subDirEmptyStr) {
        fprintf(LOGFILE, "baseDir \"%s\" is a file and cannot contain subdir \"%s\".\n", *ptr, subdir);
        return -1;
      }
      full_path = strdup(*ptr);
      needs_tt_user = 0;
    } else {
      full_path = concatenate("%s/%s", "user subdir", 2, *ptr, subdir);
    }

    if (full_path == NULL) {
      return -1;
    }
    int this_ret = delete_path(full_path, needs_tt_user);
    free(full_path);
    // delete as much as we can, but remember the error
    if (this_ret != 0) {
      ret = this_ret;
    }
  }
  return ret;
}
コード例 #11
0
ファイル: devtmpfs.c プロジェクト: Blue-Design/ev3sources
int devtmpfs_delete_node(struct device *dev)
{
	const char *tmp = NULL;
	const char *nodename;
	const struct cred *curr_cred;
	struct nameidata nd;
	struct dentry *dentry;
	struct kstat stat;
	int deleted = 1;
	int err;

	if (!dev_mnt)
		return 0;

	nodename = device_get_devnode(dev, NULL, &tmp);
	if (!nodename)
		return -ENOMEM;

	curr_cred = override_creds(&init_cred);
	err = vfs_path_lookup(dev_mnt->mnt_root, dev_mnt,
			      nodename, LOOKUP_PARENT, &nd);
	if (err)
		goto out;

	mutex_lock_nested(&nd.path.dentry->d_inode->i_mutex, I_MUTEX_PARENT);
	dentry = lookup_one_len(nd.last.name, nd.path.dentry, nd.last.len);
	if (!IS_ERR(dentry)) {
		if (dentry->d_inode) {
			err = vfs_getattr(nd.path.mnt, dentry, &stat);
			if (!err && dev_mynode(dev, dentry->d_inode, &stat)) {
				err = vfs_unlink(nd.path.dentry->d_inode,
						 dentry);
				if (!err || err == -ENOENT)
					deleted = 1;
			}
		} else {
			err = -ENOENT;
		}
		dput(dentry);
	} else {
		err = PTR_ERR(dentry);
	}
	mutex_unlock(&nd.path.dentry->d_inode->i_mutex);

	path_put(&nd.path);
	if (deleted && strchr(nodename, '/'))
		delete_path(nodename);
out:
	kfree(tmp);
	revert_creds(curr_cred);
	return err;
}
コード例 #12
0
static void
setup_reverse_path( int status, const path *p, void *user_data ) {
  assert(user_data);

  packet_out_params *params = user_data;
  if ( status != SETUP_SUCCEEDED ) {
    error( "Failed to set up path ( status = %d ).", status );
    output_packet( params->packet, params->out_datapath_id, params->out_port_no, params->out_vid );
    free_buffer( params->packet );
    xfree( params );
    return;
  }

  struct ofp_match rmatch;
  set_ipv4_reverse_match( &rmatch, &(p->match) );
  rmatch.dl_vlan = params->out_vid;

  openflow_actions *vlan_actions;
  vlan_actions = create_openflow_actions_to_update_vid( params->out_vid, params->in_vid );

  path *rpath = create_path( rmatch, p->priority, p->idle_timeout, p->hard_timeout );
  assert( rpath != NULL );
  list_element *hops = p->hops;
  dlist_element *rhops = create_dlist();
  while ( hops != NULL ) {
    hop *h = hops->data;
    assert( h != NULL );
    hop *rh = create_hop( h->datapath_id, h->out_port, h->in_port, vlan_actions );
    if ( vlan_actions ) {
      delete_actions( vlan_actions );
      vlan_actions = NULL;
    }
    assert( rh != NULL );
    rhops = insert_before_dlist( rhops, rh );
    hops = hops->next;
  }
  while ( rhops != NULL && rhops->data != NULL ) {
    append_hop_to_path( rpath, ( hop * ) rhops->data );
    rhops = rhops->next;
  }
  bool ret = setup_path( rpath, handle_setup, params, NULL, NULL );
  if ( ret != true ) {
    error( "Failed to set up reverse path." );
    output_packet( params->packet, params->out_datapath_id, params->out_port_no, params->out_vid );
    free_buffer( params->packet );
    xfree( params );
  }

  delete_path( rpath );
  delete_dlist( rhops );
}
コード例 #13
0
ファイル: devtmpfs.c プロジェクト: nos1609/Chrono_Kernel-1
static int handle_remove(const char *nodename, struct device *dev)
{
	struct nameidata nd;
	struct dentry *dentry;
	struct kstat stat;
	int deleted = 1;
	int err;

	err = kern_path_parent(nodename, &nd);
	if (err)
		return err;

	mutex_lock_nested(&nd.path.dentry->d_inode->i_mutex, I_MUTEX_PARENT);
	dentry = lookup_one_len(nd.last.name, nd.path.dentry, nd.last.len);
	if (!IS_ERR(dentry)) {
		if (dentry->d_inode) {
			err = vfs_getattr(nd.path.mnt, dentry, &stat);
			if (!err && dev_mynode(dev, dentry->d_inode, &stat)) {
				struct iattr newattrs;
				/*
				 * before unlinking this node, reset permissions
				 * of possible references like hardlinks
				 */
				newattrs.ia_uid = 0;
				newattrs.ia_gid = 0;
				newattrs.ia_mode = stat.mode & ~0777;
				newattrs.ia_valid =
					ATTR_UID|ATTR_GID|ATTR_MODE;
				mutex_lock(&dentry->d_inode->i_mutex);
				notify_change(dentry, &newattrs);
				mutex_unlock(&dentry->d_inode->i_mutex);
				err = vfs_unlink(nd.path.dentry->d_inode,
						 dentry);
				if (!err || err == -ENOENT)
					deleted = 1;
			}
		} else {
			err = -ENOENT;
		}
		dput(dentry);
	} else {
		err = PTR_ERR(dentry);
	}
	mutex_unlock(&nd.path.dentry->d_inode->i_mutex);

	path_put(&nd.path);
	if (deleted && strchr(nodename, '/'))
		delete_path(nodename);
	return err;
}
コード例 #14
0
ファイル: AStarPath.cpp プロジェクト: nuvie/nuvie
{}void AStarPath::create_path()
{    astar_node *i = final_node; // iterator through steps, from back
    delete_path();
    std::vector<astar_node *> reverse_list;
    while(i)
    {
        reverse_list.push_back(i);
        i = i->parent;
    }
    while(!reverse_list.empty())
    {
        i = reverse_list.back();
        add_step(i->loc);
        reverse_list.pop_back();
    }
    set_path_size(step_count);
}/* Get a new neighbor to nnode and score it, returning true if it's usable. */
コード例 #15
0
/*! 2017. 8.12 study -ing */
static int handle_remove(const char *nodename, struct device *dev)
{
	struct path parent;
	struct dentry *dentry;
	int deleted = 0;
	int err;

	dentry = kern_path_locked(nodename, &parent);
	if (IS_ERR(dentry))
		return PTR_ERR(dentry);

	if (dentry->d_inode) {
		struct kstat stat;
		struct path p = {.mnt = parent.mnt, .dentry = dentry};
		err = vfs_getattr(&p, &stat);
		if (!err && dev_mynode(dev, dentry->d_inode, &stat)) {
			struct iattr newattrs;
			/*
			 * before unlinking this node, reset permissions
			 * of possible references like hardlinks
			 */
			newattrs.ia_uid = GLOBAL_ROOT_UID;
			newattrs.ia_gid = GLOBAL_ROOT_GID;
			newattrs.ia_mode = stat.mode & ~0777;
			newattrs.ia_valid =
				ATTR_UID|ATTR_GID|ATTR_MODE;
			mutex_lock(&dentry->d_inode->i_mutex);
			notify_change(dentry, &newattrs, NULL);
			mutex_unlock(&dentry->d_inode->i_mutex);
			err = vfs_unlink(parent.dentry->d_inode, dentry, NULL);
			if (!err || err == -ENOENT)
				deleted = 1;
		}
	} else {
		err = -ENOENT;
	}
	dput(dentry);
	mutex_unlock(&parent.dentry->d_inode->i_mutex);

	path_put(&parent);
	if (deleted && strchr(nodename, '/'))
		delete_path(nodename);
	return err;
}
コード例 #16
0
ファイル: op_dio2.c プロジェクト: SparroHawc/ScarletDME
bool delete_path(char * path)
{
 bool status = FALSE;
 DIR * dfu;
 struct dirent * dp;
 struct stat stat_buf;
 char parent_path[MAX_PATHNAME_LEN+1];
 int parent_len;
 char sub_path[MAX_PATHNAME_LEN+1];

 /* Check path exists and get type information */

 if (stat(path, &stat_buf) != 0) goto exit_delete_path;

 if (stat_buf.st_mode & S_IFDIR)  /* It's a directory */
  {
   dfu = opendir(path);
   if (dfu == NULL) goto exit_delete_path;

   strcpy(parent_path, path);
   parent_len = strlen(parent_path);
   if (parent_path[parent_len-1] == DS) parent_path[parent_len-1] = '\0';

   while((dp = readdir(dfu)) != NULL)
    {
     if (strcmp(dp->d_name, ".") == 0) continue;
     if (strcmp(dp->d_name, "..") == 0) continue;
     sprintf(sub_path, "%s%c%s", parent_path, DS, dp->d_name);
     if (!delete_path(sub_path)) goto exit_delete_path;;
    }
   closedir(dfu);

   if (rmdir(path) != 0) goto exit_delete_path;  /* Delete the directory */
  }
 else if (stat_buf.st_mode & S_IFREG)  /* It's a file */
  {
   if (remove(path) != 0) goto exit_delete_path;
  }

status = TRUE;

exit_delete_path:
 return status;
}
コード例 #17
0
 virtual int on_reached_directory_post() override
 {
     return delete_path() ? Action::FTS_OK : Action::FTS_Fail;
 }
コード例 #18
0
ファイル: devtmpfs.c プロジェクト: jhu-chang/r6300v2
int devtmpfs_delete_node(struct device *dev)
{
	const char *tmp = NULL;
	const char *nodename;
	const struct cred *curr_cred;
	struct nameidata nd;
	struct dentry *dentry;
	struct kstat stat;
	int deleted = 1;
	int err;

	if (!dev_mnt)
		return 0;

	nodename = device_get_devnode(dev, NULL, &tmp);
	if (!nodename)
		return -ENOMEM;

	curr_cred = override_creds(&init_cred);
	err = vfs_path_lookup(dev_mnt->mnt_root, dev_mnt,
			      nodename, LOOKUP_PARENT, &nd);
	if (err)
		goto out;

	mutex_lock_nested(&nd.path.dentry->d_inode->i_mutex, I_MUTEX_PARENT);
	dentry = lookup_one_len(nd.last.name, nd.path.dentry, nd.last.len);
	if (!IS_ERR(dentry)) {
		if (dentry->d_inode) {
			err = vfs_getattr(nd.path.mnt, dentry, &stat);
			if (!err && dev_mynode(dev, dentry->d_inode, &stat)) {
				struct iattr newattrs;
				/*
				 * before unlinking this node, reset permissions
				 * of possible references like hardlinks
				 */
				newattrs.ia_uid = 0;
				newattrs.ia_gid = 0;
				newattrs.ia_mode = stat.mode & ~0777;
				newattrs.ia_valid =
					ATTR_UID|ATTR_GID|ATTR_MODE;
				mutex_lock(&dentry->d_inode->i_mutex);
				notify_change(dentry, &newattrs);
				mutex_unlock(&dentry->d_inode->i_mutex);
				err = vfs_unlink(nd.path.dentry->d_inode,
						 dentry);
				if (!err || err == -ENOENT)
					deleted = 1;
			}
		} else {
			err = -ENOENT;
		}
		dput(dentry);
	} else {
		err = PTR_ERR(dentry);
	}
	mutex_unlock(&nd.path.dentry->d_inode->i_mutex);

	path_put(&nd.path);
	if (deleted && strchr(nodename, '/'))
		delete_path(nodename);
out:
	kfree(tmp);
	revert_creds(curr_cred);
	return err;
}
コード例 #19
0
ファイル: abrt-server.c プロジェクト: credmon/abrt
static int perform_http_xact(void)
{
    /* use free instead of g_free so that we can use xstr* functions from
     * libreport/lib/xfuncs.c
     */
    GHashTable *problem_info = g_hash_table_new_full(g_str_hash, g_str_equal,
                                     free, free);
    /* Read header */
    char *body_start = NULL;
    char *messagebuf_data = NULL;
    unsigned messagebuf_len = 0;
    /* Loop until EOF/error/timeout/end_of_header */
    while (1)
    {
        messagebuf_data = xrealloc(messagebuf_data, messagebuf_len + INPUT_BUFFER_SIZE);
        char *p = messagebuf_data + messagebuf_len;
        int rd = read(STDIN_FILENO, p, INPUT_BUFFER_SIZE);
        if (rd < 0)
        {
            if (errno == EINTR) /* SIGALRM? */
                error_msg_and_die("Timed out");
            perror_msg_and_die("read");
        }
        if (rd == 0)
            break;

        log_debug("Received %u bytes of data", rd);
        messagebuf_len += rd;
        total_bytes_read += rd;
        if (total_bytes_read > MAX_MESSAGE_SIZE)
            error_msg_and_die("Message is too long, aborting");

        /* Check whether we see end of header */
        /* Note: we support both [\r]\n\r\n and \n\n */
        char *past_end = messagebuf_data + messagebuf_len;
        if (p > messagebuf_data+1)
            p -= 2; /* start search from two last bytes in last read - they might be '\n\r' */
        while (p < past_end)
        {
            p = memchr(p, '\n', past_end - p);
            if (!p)
                break;
            p++;
            if (p >= past_end)
                break;
            if (*p == '\n'
             || (*p == '\r' && p+1 < past_end && p[1] == '\n')
            ) {
                body_start = p + 1 + (*p == '\r');
                *p = '\0';
                goto found_end_of_header;
            }
        }
    } /* while (read) */
 found_end_of_header: ;
    log_debug("Request: %s", messagebuf_data);

    /* Sanitize and analyze header.
     * Header now is in messagebuf_data, NUL terminated string,
     * with last empty line deleted (by placement of NUL).
     * \r\n are not (yet) converted to \n, multi-line headers also
     * not converted.
     */
    /* First line must be "op<space>[http://host]/path<space>HTTP/n.n".
     * <space> is exactly one space char.
     */
    if (prefixcmp(messagebuf_data, "DELETE ") == 0)
    {
        messagebuf_data += strlen("DELETE ");
        char *space = strchr(messagebuf_data, ' ');
        if (!space || prefixcmp(space+1, "HTTP/") != 0)
            return 400; /* Bad Request */
        *space = '\0';
        //decode_url(messagebuf_data); %20 => ' '
        alarm(0);
        return delete_path(messagebuf_data);
    }

    /* We erroneously used "PUT /" to create new problems.
     * POST is the correct request in this case:
     * "PUT /" implies creation or replace of resource named "/"!
     * Delete PUT in 2014.
     */
    if (prefixcmp(messagebuf_data, "PUT ") != 0
     && prefixcmp(messagebuf_data, "POST ") != 0
    ) {
        return 400; /* Bad Request */
    }

    enum {
        CREATION_NOTIFICATION,
        CREATION_REQUEST,
    };
    int url_type;
    char *url = skip_non_whitespace(messagebuf_data) + 1; /* skip "POST " */
    if (prefixcmp(url, "/creation_notification ") == 0)
        url_type = CREATION_NOTIFICATION;
    else if (prefixcmp(url, "/ ") == 0)
        url_type = CREATION_REQUEST;
    else
        return 400; /* Bad Request */

    /* Read body */
    if (!body_start)
    {
        log_warning("Premature EOF detected, exiting");
        return 400; /* Bad Request */
    }

    messagebuf_len -= (body_start - messagebuf_data);
    memmove(messagebuf_data, body_start, messagebuf_len);
    log_debug("Body so far: %u bytes, '%s'", messagebuf_len, messagebuf_data);

    /* Loop until EOF/error/timeout */
    while (1)
    {
        if (url_type == CREATION_REQUEST)
        {
            while (1)
            {
                unsigned len = strnlen(messagebuf_data, messagebuf_len);
                if (len >= messagebuf_len)
                    break;
                /* messagebuf has at least one NUL - process the line */
                process_message(problem_info, messagebuf_data);
                messagebuf_len -= (len + 1);
                memmove(messagebuf_data, messagebuf_data + len + 1, messagebuf_len);
            }
        }

        messagebuf_data = xrealloc(messagebuf_data, messagebuf_len + INPUT_BUFFER_SIZE + 1);
        int rd = read(STDIN_FILENO, messagebuf_data + messagebuf_len, INPUT_BUFFER_SIZE);
        if (rd < 0)
        {
            if (errno == EINTR) /* SIGALRM? */
                error_msg_and_die("Timed out");
            perror_msg_and_die("read");
        }
        if (rd == 0)
            break;

        log_debug("Received %u bytes of data", rd);
        messagebuf_len += rd;
        total_bytes_read += rd;
        if (total_bytes_read > MAX_MESSAGE_SIZE)
            error_msg_and_die("Message is too long, aborting");
    }

    /* Body received, EOF was seen. Don't let alarm to interrupt after this. */
    alarm(0);

    int ret = 0;
    if (url_type == CREATION_NOTIFICATION)
    {
        if (client_uid != 0)
        {
            error_msg("UID=%ld is not authorized to trigger post-create processing", (long)client_uid);
            ret = 403; /* Forbidden */
            goto out;
        }

        messagebuf_data[messagebuf_len] = '\0';
        return run_post_create(messagebuf_data);
    }

    /* Save problem dir */
    unsigned pid = convert_pid(problem_info);
    die_if_data_is_missing(problem_info);

    char *executable = g_hash_table_lookup(problem_info, FILENAME_EXECUTABLE);
    if (executable)
    {
        char *last_file = concat_path_file(g_settings_dump_location, "last-via-server");
        int repeating_crash = check_recent_crash_file(last_file, executable);
        free(last_file);
        if (repeating_crash) /* Only pretend that we saved it */
        {
            error_msg("Not saving repeating crash in '%s'", executable);
            goto out; /* ret is 0: "success" */
        }
    }

#if 0
//TODO:
    /* At least it should generate local problem identifier UUID */
    problem_data_add_basics(problem_info);
//...the problem being that problem_info here is not a problem_data_t!
#endif

    create_problem_dir(problem_info, pid);
    /* does not return */

 out:
    g_hash_table_destroy(problem_info);
    return ret; /* Used as HTTP response code */
}
コード例 #20
0
 virtual int on_reached_special_file() override
 {
     return delete_path() ? Action::FTS_OK : Action::FTS_Fail;
 }
コード例 #21
0
 virtual int on_reached_symlink() override
 {
     return delete_path() ? Action::FTS_OK : Action::FTS_Fail;
 }
コード例 #22
0
ファイル: op_dio2.c プロジェクト: SparroHawc/ScarletDME
void op_ospath()
{
 /* Stack:

     |================================|=============================|
     |            BEFORE              |           AFTER             |
     |================================|=============================|
 top |  Key                           | Information                 |
     |--------------------------------|-----------------------------| 
     |  Pathname string               |                             |
     |================================|=============================|

 Key values:           Action                             Returns
     0  OS_PATHNAME    Test if valid pathname             True/False
     1  OS_FILENAME    Test if valid filename             True/False
                       or directory file record name
     2  OS_EXISTS      Test if file exists                True/False
     3  OS_UNIQUE      Make a unique file name            Name
     4  OS_FULLPATH    Return full pathname               Name
     5  OS_DELETE      Delete file                        Success/Failure
     6  OS_CWD         Get current working directory      Pathname
     7  OS_DTM         Return date/time modified          DTM value
     8  OS_FLUSH_CACHE Flush DH file cache                -
     9  OS_CD          Change working directory           Success/Failure
    10  OS_MAPPED_NAME Map a directory file name          Mapped name
    11  OS_OPEN        Check if path is an open file      True/False
    12  OS_DIR         Return content of directory        Filenames
    13  OS_MKDIR       Make a directory                   True/False
    14  OS_MKPATH      Make a directory path              True/False

 Pathnames with lengths outside the range 1 to MAX_PATHNAME_LEN return
 0 regardless of the action key.

 */

 long int status = 0;
 short int key;
 DESCRIPTOR * descr;
 char path[MAX_PATHNAME_LEN+1];
 short int path_len;
 char name[MAX_PATHNAME_LEN+1];
 char * p;
 char * q;
 STRING_CHUNK * head;
 int file_id;
 FILE_ENTRY * fptr;
 struct stat stat_buff;
 DIR * dfu;
 struct dirent * dp;
 long int n;

 /* Get action key */

 descr = e_stack - 1;
 GetInt(descr);
 key = (short int)(descr->data.value);
 k_pop(1);

 /* Get pathname */

 descr = e_stack - 1;
 path_len = k_get_c_string(descr, path, MAX_PATHNAME_LEN);
 k_dismiss();
 if (path_len < 0) goto set_status;
#ifdef CASE_INSENSITIVE_FILE_SYSTEM
 UpperCaseString(path);
#endif

 switch(key)
  {
   case OS_PATHNAME:     /* Test if valid pathname */
      p = path;
      if (*p == '/') p++;

      do {
          q = strchr(p, '/');
          if (q != NULL) *q = '\0';
          if (!valid_name(p)) goto set_status;
          p = q + 1;
         } while(q != NULL);
      status = 1;


      break;

   case OS_FILENAME:     /* Test if valid pathname */
      status = (long int)valid_name(path);
      break;

   case OS_EXISTS:     /* Test if file exists */
      status = !access(path, 0);
      break;

   case OS_UNIQUE:  /* Make unique file name. Path variable holds directory name */
      n = (time(NULL) * 10) & 0xFFFFFFFL;
      do {
          sprintf(name, "%s\\D%07lX", path, n);
          n--;
         } while(!access(name, 0));
      sprintf(name, "D%07lX", n);
      k_put_c_string(name, e_stack);
      e_stack++;
      goto exit_op_pathinfo;

   case OS_FULLPATH:     /* Expand path to full OS pathname */
      fullpath(name, path);
      k_put_c_string(name, e_stack);
      e_stack++;
      goto exit_op_pathinfo;

   case OS_DELETE:
      flush_dh_cache();
      status = (long int)delete_path(path);
      break;

   case OS_CWD:
      (void)getcwd(name, MAX_PATHNAME_LEN);
#ifdef CASE_INSENSITIVE_FILE_SYSTEM
      UpperCaseString(name);
#endif
      k_put_c_string(name, e_stack);
      e_stack++;
      goto exit_op_pathinfo;

   case OS_DTM:
      if (stat(path, &stat_buff) == 0) status = stat_buff.st_mtime;
      break;

   case OS_FLUSH_CACHE:
      flush_dh_cache();
      break;

   case OS_CD:
      status = attach(path);
      break;

   case OS_MAPPED_NAME:    /* Map a directory file record name */
      (void)map_t1_id(path, strlen(path), name);
      k_put_c_string(name, e_stack);
      e_stack++;
      goto exit_op_pathinfo;

   case OS_OPEN:
      fullpath(name, path);
      for(file_id = 1; file_id <= sysseg->used_files; file_id++)
       {
        fptr = FPtr(file_id);
        if ((fptr->ref_ct != 0)
          && (strcmp((char *)(fptr->pathname), name) == 0))
         {
          status = TRUE;
          break;
         }
       }
      break;

   case OS_DIR:
      head = NULL;
      ts_init(&head, 1024);
      if ((dfu = opendir(path)) != NULL)
       {
        if (path[path_len-1] == DS) path[path_len-1] = '\0';

        while((dp = readdir(dfu)) != NULL)
         {
          if (strcmp(dp->d_name, ".") == 0) continue;
          if (strcmp(dp->d_name, "..") == 0) continue;

          sprintf(name, "%s%c%s", path, DS, dp->d_name);
          if (stat(name, &stat_buff)) continue;

          strcpy(name+1, dp->d_name);
#ifdef CASE_INSENSITIVE_FILE_SYSTEM
          UpperCaseString(name+1);
#endif
          if (stat_buff.st_mode & S_IFDIR)
           {
            name[0] = 'D';
            if (head != NULL) ts_copy_byte(FIELD_MARK);
            ts_copy_c_string(name);
           }
          else if (stat_buff.st_mode & S_IFREG)
           {
            name[0] = 'F';
            if (head != NULL) ts_copy_byte(FIELD_MARK);
            ts_copy_c_string(name);
           }
         }

        closedir(dfu);
       }
      ts_terminate();
      InitDescr(e_stack, STRING);
      (e_stack++)->data.str.saddr = head;
      goto exit_op_pathinfo;      

   case OS_MKDIR:
      status = !MakeDirectory(path);
      break;

   case OS_MKPATH:
      status = make_path(path);
      break;
       
   default:
      k_error(sysmsg(1010));
  }

set_status:

 /* Set status value on stack */

 InitDescr(e_stack, INTEGER);
 (e_stack++)->data.value = status;

exit_op_pathinfo:
 return;
}