*/
struct GNUNET_FS_ShareTreeItem *pos;
+ /**
+ * Task scheduled when we are done.
+ */
+ GNUNET_SCHEDULER_TaskIdentifier stop_task;
+
/**
* Arguments for helper.
*/
/**
- * Abort the scan.
+ * Abort the scan. Must not be called from within the progress_callback
+ * function.
*
* @param ds directory scanner structure
*/
/* free resources */
if (NULL != ds->toplevel)
GNUNET_FS_share_tree_free (ds->toplevel);
+ if (GNUNET_SCHEDULER_NO_TASK != ds->stop_task)
+ GNUNET_SCHEDULER_cancel (ds->stop_task);
GNUNET_free_non_null (ds->ex_arg);
GNUNET_free (ds->filename_expanded);
GNUNET_free (ds);
GNUNET_assert (NULL != pos);
moved = 0; /* must not terminate, even on file, otherwise "normal" */
- while ( (pos->is_directory) ||
+ while ( (pos->is_directory == GNUNET_YES) ||
(0 == moved) )
{
if ( (moved != -1) &&
int is_directory)
{
struct GNUNET_FS_ShareTreeItem *chld;
+ size_t slen;
chld = GNUNET_malloc (sizeof (struct GNUNET_FS_ShareTreeItem));
chld->parent = parent;
chld->filename = GNUNET_strdup (filename);
- chld->short_filename = GNUNET_strdup (GNUNET_STRINGS_get_short_name (filename));
+ GNUNET_asprintf (&chld->short_filename,
+ "%s%s",
+ GNUNET_STRINGS_get_short_name (filename),
+ is_directory == GNUNET_YES ? "/" : "");
+ /* make sure we do not end with '//' */
+ slen = strlen (chld->short_filename);
+ if ( (slen >= 2) &&
+ (chld->short_filename[slen-1] == '/') &&
+ (chld->short_filename[slen-2] == '/') )
+ chld->short_filename[slen-1] = '\0';
chld->is_directory = is_directory;
if (NULL != parent)
GNUNET_CONTAINER_DLL_insert (parent->children_head,
}
+/**
+ * Task run last to shut everything down.
+ *
+ * @param cls the 'struct GNUNET_FS_DirScanner'
+ * @param tc unused
+ */
+static void
+finish_scan (void *cls,
+ const struct GNUNET_SCHEDULER_TaskContext *tc)
+{
+ struct GNUNET_FS_DirScanner *ds = cls;
+
+ ds->stop_task = GNUNET_SCHEDULER_NO_TASK;
+ GNUNET_HELPER_stop (ds->helper);
+ ds->helper = NULL;
+ ds->progress_callback (ds->progress_callback_cls,
+ NULL, GNUNET_SYSERR,
+ GNUNET_FS_DIRSCANNER_FINISHED);
+}
+
+
/**
* Called every time there is data to read from the scanner.
* Calls the scanner progress handler.
ds->progress_callback (ds->progress_callback_cls,
filename, GNUNET_NO,
GNUNET_FS_DIRSCANNER_FILE_START);
- expand_tree (ds->pos,
- filename, GNUNET_NO);
+ if (NULL == ds->toplevel)
+ ds->toplevel = expand_tree (ds->pos,
+ filename, GNUNET_NO);
+ else
+ (void) expand_tree (ds->pos,
+ filename, GNUNET_NO);
return;
case GNUNET_MESSAGE_TYPE_FS_PUBLISH_HELPER_PROGRESS_DIRECTORY:
if (filename[left-1] != '\0')
GNUNET_break (0);
break;
}
+ if (NULL == ds->toplevel)
+ {
+ GNUNET_break (0);
+ break;
+ }
ds->progress_callback (ds->progress_callback_cls,
NULL, GNUNET_SYSERR,
GNUNET_FS_DIRSCANNER_ALL_COUNTED);
ds->pos = ds->toplevel;
- if (ds->pos->is_directory)
+ if (ds->pos->is_directory == GNUNET_YES)
ds->pos = advance (ds->pos);
return;
case GNUNET_MESSAGE_TYPE_FS_PUBLISH_HELPER_META_DATA:
GNUNET_CONTAINER_meta_data_delete (ds->pos->meta,
EXTRACTOR_METATYPE_FILENAME,
NULL, 0);
+ /* instead, put in our 'safer' original filename */
GNUNET_CONTAINER_meta_data_insert (ds->pos->meta, "<libgnunetfs>",
- EXTRACTOR_METATYPE_FILENAME,
+ EXTRACTOR_METATYPE_GNUNET_ORIGINAL_FILENAME,
EXTRACTOR_METAFORMAT_UTF8, "text/plain",
ds->pos->short_filename,
strlen (ds->pos->short_filename) + 1);
}
+ ds->pos->ksk_uri = GNUNET_FS_uri_ksk_create_from_meta_data (ds->pos->meta);
ds->pos = advance (ds->pos);
return;
}
break;
}
if (0 != left)
+ {
+ GNUNET_break (0);
+ break;
+ }
+ if (NULL == ds->toplevel)
{
GNUNET_break (0);
break;
}
- GNUNET_HELPER_stop (ds->helper);
- ds->helper = NULL;
- ds->progress_callback (ds->progress_callback_cls,
- NULL, GNUNET_SYSERR,
- GNUNET_FS_DIRSCANNER_FINISHED);
+ ds->stop_task = GNUNET_SCHEDULER_add_now (&finish_scan,
+ ds);
return;
default:
GNUNET_break (0);
ds->progress_callback (ds->progress_callback_cls,
NULL, GNUNET_SYSERR,
GNUNET_FS_DIRSCANNER_INTERNAL_ERROR);
-
}
* Start a directory scanner thread.
*
* @param filename name of the directory to scan
- * @param GNUNET_YES to not to run libextractor on files (only build a tree)
+ * @param disable_extractor GNUNET_YES to not to run libextractor on files (only build a tree)
* @param ex if not NULL, must be a list of extra plugins for extractor
* @param cb the callback to call when there are scanning progress messages
* @param cb_cls closure for 'cb'