During my testing of Ecore_Con, I found some little bug when you are doing 
multiple download simultaneously :

        - The data buffer we are receiving must be copied, or it could be 
reused by curl and we will receive garbage in the event handler.
        - Sometime the complete event show up before we receive the last chunk 
of data. I put all the complete event inside a list and the event are send 
inside an ecore_idler.

I also added some functionnality :
        - Use ECORE_MAGIC.
        - The status code is no longer curl internal status, but ftp or http 
return code (I think it's more usefull than CURLE_OK).
        - You can now add a time condition on you requested url (see HTTP code 
304).
        - Normally we must receive progress events also (I admit I didn't test 
if it worked fine, but it should).

I used this modified ecore_con_url to developpe a library downloading file in a 
cache directory cleanly. I needed to include it inside Ecore as I wanted to use 
some ecore private facility like ECORE_MAGIC. I attached the patch if people 
are interested.

Cedric

diff -Nrau -X exclude.cvs e17-clean/libs/ecore/src/lib/ecore_con/Ecore_Con.h e17-dev/libs/ecore/src/lib/ecore_con/Ecore_Con.h
--- e17-clean/libs/ecore/src/lib/ecore_con/Ecore_Con.h	2007-03-20 18:54:38.000000000 +0100
+++ e17-dev/libs/ecore/src/lib/ecore_con/Ecore_Con.h	2007-08-08 20:30:15.000000000 +0200
@@ -76,7 +76,15 @@
 	ECORE_CON_REMOTE_SYSTEM,
 	ECORE_CON_USE_SSL = 16
      } Ecore_Con_Type;
-   
+
+   typedef enum _Ecore_Con_Url_Time
+     {
+        ECORE_CON_URL_TIME_NONE = 0,
+        ECORE_CON_URL_TIME_IFMODSINCE,
+        ECORE_CON_URL_TIME_IFUNMODSINCE,
+        ECORE_CON_URL_TIME_LASTMOD
+     } Ecore_Con_Url_Time;
+
    typedef struct _Ecore_Con_Event_Client_Add  Ecore_Con_Event_Client_Add;
    typedef struct _Ecore_Con_Event_Client_Del  Ecore_Con_Event_Client_Del;
    typedef struct _Ecore_Con_Event_Server_Add  Ecore_Con_Event_Server_Add;
@@ -85,6 +93,8 @@
    typedef struct _Ecore_Con_Event_Server_Data Ecore_Con_Event_Server_Data;
    typedef struct _Ecore_Con_Event_Url_Data Ecore_Con_Event_Url_Data;
    typedef struct _Ecore_Con_Event_Url_Complete Ecore_Con_Event_Url_Complete;
+   typedef struct _Ecore_Con_Event_Url_Progress_Upload Ecore_Con_Event_Url_Progress_Upload;
+   typedef struct _Ecore_Con_Event_Url_Progress_Download Ecore_Con_Event_Url_Progress_Download;
 
    struct _Ecore_Con_Event_Client_Add
      {
@@ -132,7 +142,21 @@
 	Ecore_Con_Url    *url_con;
 	int               status;
      };
-	 
+
+   struct _Ecore_Con_Event_Url_Progress_Download
+     {
+        Ecore_Con_Url                   *url_con;
+        double                           total;
+        double                           now;
+     };
+
+   struct _Ecore_Con_Event_Url_Progress_Upload
+     {
+        Ecore_Con_Url                   *url_con;
+        double                           total;
+        double                           now;
+     };
+
    EAPI extern int ECORE_CON_EVENT_CLIENT_ADD;
    EAPI extern int ECORE_CON_EVENT_CLIENT_DEL;
    EAPI extern int ECORE_CON_EVENT_SERVER_ADD;
@@ -141,6 +165,8 @@
    EAPI extern int ECORE_CON_EVENT_SERVER_DATA;
    EAPI extern int ECORE_CON_EVENT_URL_DATA;
    EAPI extern int ECORE_CON_EVENT_URL_COMPLETE;
+   EAPI extern int ECORE_CON_EVENT_URL_PROGRESS_DOWNLOAD;
+   EAPI extern int ECORE_CON_EVENT_URL_PROGRESS_UPLOAD;
    
    EAPI int               ecore_con_init(void);
    EAPI int               ecore_con_shutdown(void);
@@ -171,8 +197,11 @@
    EAPI int               ecore_con_url_shutdown(void);
    EAPI Ecore_Con_Url    *ecore_con_url_new(const char *url);
    EAPI void              ecore_con_url_destroy(Ecore_Con_Url *url_con);
+   EAPI void             *ecore_con_url_data_set(Ecore_Con_Url *url_con, const void *data);
+   EAPI void             *ecore_con_url_data_get(Ecore_Con_Url *url_con);
    EAPI int               ecore_con_url_url_set(Ecore_Con_Url *url_con, const char *url);
    EAPI int               ecore_con_url_send(Ecore_Con_Url *url_con, void *data, size_t length, char *content_type);
+   EAPI void              ecore_con_url_time(Ecore_Con_Url *url_con, Ecore_Con_Url_Time condition, time_t tm);
 
    EAPI int               ecore_con_dns_lookup(const char *name,
 					       void (*done_cb)(void *data, struct hostent *hostent),
diff -Nrau -X exclude.cvs e17-clean/libs/ecore/src/lib/ecore_con/ecore_con_private.h e17-dev/libs/ecore/src/lib/ecore_con/ecore_con_private.h
--- e17-clean/libs/ecore/src/lib/ecore_con/ecore_con_private.h	2007-03-20 18:54:38.000000000 +0100
+++ e17-dev/libs/ecore/src/lib/ecore_con/ecore_con_private.h	2007-08-08 20:23:46.000000000 +0200
@@ -6,6 +6,7 @@
 
 #define ECORE_MAGIC_CON_SERVER             0x77665544
 #define ECORE_MAGIC_CON_CLIENT             0x77556677
+#define ECORE_MAGIC_CON_URL                0x77074255
 
 #if USE_OPENSSL
 #include <openssl/ssl.h>
@@ -66,12 +67,18 @@
 #ifdef HAVE_CURL
 struct _Ecore_Con_Url
 {
-   /* FIXME: ECORE_MAGIC ? */
-   CURL             *curl_easy;
-   char             *url;
+   ECORE_MAGIC;
+   CURL              *curl_easy;
    struct curl_slist *headers;
-   Ecore_Fd_Handler *fd_handler;
-   char              active : 1;
+   char              *url;
+
+   Ecore_Con_Url_Time condition;
+   time_t             time;
+   const void        *data;
+
+   Ecore_Fd_Handler  *fd_handler;
+
+   char               active : 1;
 };
 #endif
 
diff -Nrau -X exclude.cvs e17-clean/libs/ecore/src/lib/ecore_con/ecore_con_url.c e17-dev/libs/ecore/src/lib/ecore_con/ecore_con_url.c
--- e17-clean/libs/ecore/src/lib/ecore_con/ecore_con_url.c	2007-08-06 16:51:03.000000000 +0200
+++ e17-dev/libs/ecore/src/lib/ecore_con/ecore_con_url.c	2007-09-14 20:54:37.000000000 +0200
@@ -44,17 +44,64 @@
 static int _ecore_con_url_fd_handler(void *data, Ecore_Fd_Handler *fd_handler);
 static int _ecore_con_url_perform(Ecore_Con_Url *url_con);
 static size_t _ecore_con_url_data_cb(void *buffer, size_t size, size_t nmemb, void *userp);
-static void _ecore_con_event_url_complete_free(void *data __UNUSED__, void *ev);
-static void _ecore_con_event_url_data_free(void *data __UNUSED__, void *ev);
+static int _ecore_con_url_progress_cb(void *clientp, double dltotal, double dlnow, double ultotal, double ulnow);
+static void _ecore_con_event_url_free(void *data __UNUSED__, void *ev);
 static int _ecore_con_url_process_completed_jobs(Ecore_Con_Url *url_con_to_match);
 
 int ECORE_CON_EVENT_URL_DATA = 0;
 int ECORE_CON_EVENT_URL_COMPLETE = 0;
+int ECORE_CON_EVENT_URL_PROGRESS_DOWNLOAD = 0;
+int ECORE_CON_EVENT_URL_PROGRESS_UPLOAD = 0;
 
 static CURLM *curlm = NULL;
 static Ecore_List *_url_con_list = NULL;
 static fd_set _current_fd_set;
 static int init_count = 0;
+
+static Ecore_Idler *_url_complete_idler = NULL;
+static Ecore_List *_url_complete_list = NULL;
+
+struct _litle_ecore_con_url_event_s
+{
+  int    type;
+  void  *ev;
+};
+typedef struct _litle_ecore_con_url_event_s     _litle_ecore_con_url_event_t;
+
+static int
+_url_complete_idler_cb(void *data)
+{
+   _litle_ecore_con_url_event_t *lev;
+
+   ecore_list_first_goto(_url_complete_list);
+   while ((lev = ecore_list_current(_url_complete_list)))
+     {
+        ecore_event_add(lev->type, lev->ev, _ecore_con_event_url_free, NULL);
+        ecore_list_remove(_url_complete_list);
+        free(lev);
+     }
+
+   ecore_idler_del(_url_complete_idler);
+   _url_complete_idler = NULL;
+
+   return 1;
+}
+
+static void
+_url_complete_push_event(int type, void *ev)
+{
+   _litle_ecore_con_url_event_t *lev;
+
+   lev = malloc(sizeof (_litle_ecore_con_url_event_t));
+   lev->type = type;
+   lev->ev = ev;
+
+   ecore_list_append(_url_complete_list, lev);
+
+   if (_url_complete_idler == NULL)
+     _url_complete_idler = ecore_idler_add(_url_complete_idler_cb, NULL);
+}
+
 #endif
 
 EAPI int
@@ -65,6 +112,8 @@
      {
 	ECORE_CON_EVENT_URL_DATA = ecore_event_type_new();
 	ECORE_CON_EVENT_URL_COMPLETE = ecore_event_type_new();
+        ECORE_CON_EVENT_URL_PROGRESS_DOWNLOAD = ecore_event_type_new();
+        ECORE_CON_EVENT_URL_PROGRESS_UPLOAD = ecore_event_type_new();
      }
 
    if (!_url_con_list)
@@ -73,6 +122,12 @@
 	if (!_url_con_list) return 0;
      }
 
+   if (!_url_complete_list)
+     {
+        _url_complete_list = ecore_list_new();
+        if (!_url_complete_list) return 0;
+     }
+
    if (!curlm)
      {
 	FD_ZERO(&_current_fd_set);
@@ -127,6 +182,12 @@
 	curlm = NULL;
      }
 
+   if (_url_complete_list)
+     {
+        ecore_list_destroy(_url_complete_list);
+        _url_complete_list = NULL;
+     }
+
    curl_global_cleanup();
 #endif
    return 1;
@@ -149,11 +210,18 @@
 	free(url_con);
 	return NULL;
      }
-   
+
+   ECORE_MAGIC_SET(url_con, ECORE_MAGIC_CON_URL);
+
    ecore_con_url_url_set(url_con, url);
 
    curl_easy_setopt(url_con->curl_easy, CURLOPT_WRITEFUNCTION, _ecore_con_url_data_cb);
    curl_easy_setopt(url_con->curl_easy, CURLOPT_WRITEDATA, url_con);
+
+   curl_easy_setopt(url_con->curl_easy, CURLOPT_PROGRESSFUNCTION, _ecore_con_url_progress_cb);
+   curl_easy_setopt(url_con->curl_easy, CURLOPT_PROGRESSDATA, url_con);
+   curl_easy_setopt(url_con->curl_easy, CURLOPT_NOPROGRESS, FALSE);
+
    /*
     * FIXME: Check that these timeouts are sensible defaults
     * FIXME: Provide a means to change these timeouts
@@ -174,7 +242,13 @@
 {
 #ifdef HAVE_CURL
    if (!url_con) return;
+   if (!ECORE_MAGIC_CHECK(url_con, ECORE_MAGIC_CON_URL))
+     {
+        ECORE_MAGIC_FAIL(url_con, ECORE_MAGIC_CON_URL, "ecore_con_url_destroy");
+        return ;
+     }
 
+   ECORE_MAGIC_SET(url_con, ECORE_MAGIC_NONE);
    if (url_con->fd_handler)
      ecore_main_fd_handler_del(url_con->fd_handler);
    if (url_con->curl_easy)
@@ -195,6 +269,12 @@
 ecore_con_url_url_set(Ecore_Con_Url *url_con, const char *url)
 {
 #ifdef HAVE_CURL
+   if (!ECORE_MAGIC_CHECK(url_con, ECORE_MAGIC_CON_URL))
+     {
+        ECORE_MAGIC_FAIL(url_con, ECORE_MAGIC_CON_URL, "ecore_con_url_url_set");
+        return 0;
+     }
+
    if (url_con->active) return 0;
 
    free(url_con->url);
@@ -209,12 +289,79 @@
    return 1;
 }
 
+EAPI void*
+ecore_con_url_data_set(Ecore_Con_Url *url_con, const void *data)
+{
+#ifdef HAVE_CURL
+   const void*  result;
+
+   if (!ECORE_MAGIC_CHECK(url_con, ECORE_MAGIC_CON_URL))
+     {
+        ECORE_MAGIC_FAIL(url_con, ECORE_MAGIC_CON_URL, "ecore_con_url_data_set");
+        return NULL;
+     }
+
+   result = url_con->data;
+   url_con->data = data;
+
+   return (void*) result;
+#else
+   (void*) url_con;
+   (const void*) data;
+
+   return NULL;
+#endif
+}
+
+EAPI void*
+ecore_con_url_data_get(Ecore_Con_Url *url_con)
+{
+#ifdef HAVE_CURL
+   if (!ECORE_MAGIC_CHECK(url_con, ECORE_MAGIC_CON_URL))
+     {
+        ECORE_MAGIC_FAIL(url_con, ECORE_MAGIC_CON_URL, "ecore_con_url_data_get");
+        return NULL;
+     }
+
+   return (void*) url_con->data;
+#else
+   (void*) url_con;
+
+   return NULL;
+#endif
+}
+
+EAPI void
+ecore_con_url_time(Ecore_Con_Url *url_con, Ecore_Con_Url_Time condition, time_t tm)
+{
+#ifdef HAVE_CURL
+   if (!ECORE_MAGIC_CHECK(url_con, ECORE_MAGIC_CON_URL))
+     {
+        ECORE_MAGIC_FAIL(url_con, ECORE_MAGIC_CON_URL, "ecore_con_url_time");
+        return ;
+     }
+
+   url_con->condition = condition;
+   url_con->time = tm;
+#else
+   (void*) url_con;
+   condition;
+   tm;
+#endif
+}
+
 EAPI int
 ecore_con_url_send(Ecore_Con_Url *url_con, void *data, size_t length, char *content_type)
 {
 #ifdef HAVE_CURL
    char tmp[256];
 
+   if (!ECORE_MAGIC_CHECK(url_con, ECORE_MAGIC_CON_URL))
+     {
+        ECORE_MAGIC_FAIL(url_con, ECORE_MAGIC_CON_URL, "ecore_con_url_send");
+        return 0;
+     }
+
    if (url_con->active) return 0;
    if (!url_con->url) return 0;
 
@@ -235,6 +382,25 @@
 	url_con->headers = curl_slist_append(url_con->headers, tmp);
      }
 
+   switch (url_con->condition)
+     {
+      case ECORE_CON_URL_TIME_NONE:
+         curl_easy_setopt(url_con->curl_easy, CURLOPT_TIMECONDITION, CURL_TIMECOND_NONE);
+         break;
+      case ECORE_CON_URL_TIME_IFMODSINCE:
+         curl_easy_setopt(url_con->curl_easy, CURLOPT_TIMECONDITION, CURL_TIMECOND_IFMODSINCE);
+         curl_easy_setopt(url_con->curl_easy, CURLOPT_TIMEVALUE, url_con->time);
+         break;
+      case ECORE_CON_URL_TIME_IFUNMODSINCE:
+         curl_easy_setopt(url_con->curl_easy, CURLOPT_TIMECONDITION, CURL_TIMECOND_IFUNMODSINCE);
+         curl_easy_setopt(url_con->curl_easy, CURLOPT_TIMEVALUE, url_con->time);
+         break;
+      case ECORE_CON_URL_TIME_LASTMOD:
+         curl_easy_setopt(url_con->curl_easy, CURLOPT_TIMECONDITION, CURL_TIMECOND_LASTMOD);
+         curl_easy_setopt(url_con->curl_easy, CURLOPT_TIMEVALUE, url_con->time);
+         break;
+     }
+
    curl_easy_setopt(url_con->curl_easy, CURLOPT_HTTPHEADER, url_con->headers);
 
    return _ecore_con_url_perform(url_con);
@@ -256,18 +422,46 @@
    size_t real_size = size * nmemb;
 
    url_con = (Ecore_Con_Url *)userp;
-   e = calloc(1, sizeof(Ecore_Con_Event_Url_Data));
+   e = calloc(1, sizeof(Ecore_Con_Event_Url_Data) + sizeof(char) * real_size);
    if (e)
      {
 	e->url_con = url_con;
-	e->data = buffer;
+	e->data = (void*) ((Ecore_Con_Event_Url_Data*)(e + 1));
 	e->size = real_size;
+        memcpy(e->data, buffer, real_size);
 	ecore_event_add(ECORE_CON_EVENT_URL_DATA, e,
-			_ecore_con_event_url_data_free, NULL);
+			_ecore_con_event_url_free, NULL);
      }
    return real_size;
 }
 
+#define ECORE_CON_URL_TRANSMISSION(Transmit, Event, Url_con, Total, Now) \
+        { \
+                Ecore_Con_Event_Url_Progress_##Transmit *e; \
+                if (Total != 0 || Now != 0) { \
+                        e = calloc(1, sizeof(Ecore_Con_Event_Url_Progress_##Transmit)); \
+                        if (e) { \
+                                e->url_con = url_con; \
+                                e->total = Total; \
+                                e->now = Now; \
+                                ecore_event_add(Event, e, _ecore_con_event_url_free, NULL); \
+                        } \
+                } \
+        }
+
+static int
+_ecore_con_url_progress_cb(void *clientp, double dltotal, double dlnow, double ultotal, double ulnow)
+{
+   Ecore_Con_Url *url_con;
+
+   url_con = clientp;
+
+   ECORE_CON_URL_TRANSMISSION(Download, ECORE_CON_EVENT_URL_PROGRESS_DOWNLOAD, url_con, dltotal, dlnow);
+   ECORE_CON_URL_TRANSMISSION(Upload, ECORE_CON_EVENT_URL_PROGRESS_UPLOAD, url_con, ultotal, ulnow);
+
+   return 0;
+}
+
 /*
  * FIXME: Use
  *   CURLOPT_PROGRESSFUNCTION and CURLOPT_PROGRESSDATA to
@@ -373,7 +567,6 @@
 		       url_con->fd_handler = NULL;
 		    }
 		  ecore_list_remove(_url_con_list);
-		  curl_multi_remove_handle(curlm, url_con->curl_easy);
 		  url_con->active = 0;
 		    {
 		       Ecore_Con_Event_Url_Complete *e;
@@ -381,11 +574,14 @@
 		       if (e)
 			 {
 			    e->url_con = url_con;
-			    e->status = curlmsg->data.result;
-			    ecore_event_add(ECORE_CON_EVENT_URL_COMPLETE, e,
-					    _ecore_con_event_url_complete_free, NULL);
+
+                            e->status = 0;
+                            curl_easy_getinfo(curlmsg->easy_handle, CURLINFO_RESPONSE_CODE, &e->status);
+
+                            _url_complete_push_event(ECORE_CON_EVENT_URL_COMPLETE, e);
 			 }
 		    }
+		  curl_multi_remove_handle(curlm, url_con->curl_easy);
 		  break;
 	       }
 	     ecore_list_next(_url_con_list);
@@ -394,20 +590,9 @@
    return job_matched;
 }
 static void
-_ecore_con_event_url_data_free(void *data __UNUSED__, void *ev)
+_ecore_con_event_url_free(void *data __UNUSED__, void *ev)
 {
-   Ecore_Con_Event_Url_Data *e;
-
-   e = ev;
-   free(e);
+   free(ev);
 }
 
-static void
-_ecore_con_event_url_complete_free(void *data __UNUSED__, void *ev)
-{
-   Ecore_Con_Event_Url_Complete *e;
-
-   e = ev;
-   free(e);
-}
 #endif
diff -Nrau -X exclude.cvs e17-clean/libs/ecore/configure.in e17-dev/libs/ecore/configure.in
--- e17-clean/libs/ecore/configure.in	2007-08-06 16:51:03.000000000 +0200
+++ e17-dev/libs/ecore/configure.in	2007-09-15 19:51:16.000000000 +0200
@@ -805,6 +830,7 @@
 AC_SUBST(requirements_ecore_config)
 AC_SUBST(requirements_ecore_desktop)
 AC_SUBST(requirements_ecore_directfb)
+AC_SUBST(requirements_ecore_download)
 AC_SUBST(requirements_ecore_evas)
 AC_SUBST(requirements_ecore_fb)
 AC_SUBST(requirements_ecore_file)
@@ -823,6 +849,7 @@
 AM_CONDITIONAL(BUILD_ECORE_EVAS_DIRECTFB, test $have_ecore_evas_dfb = yes)
 AM_CONDITIONAL(BUILD_ECORE_EVAS_FB, test $have_ecore_evas_fb = yes)
 AM_CONDITIONAL(BUILD_ECORE_EVAS_BUFFER, test $have_ecore_evas_buffer = yes)
+AM_CONDITIONAL(BUILD_ECORE_DOWNLOAD, test "x$have_ecore_download" = "xyes")
 
 AC_OUTPUT([
 Makefile
@@ -830,6 +857,7 @@
 ecore-config.pc
 ecore-desktop.pc
 ecore-directfb.pc
+ecore-download.pc
 ecore-evas.pc
 ecore-fb.pc
 ecore-file.pc
@@ -849,6 +877,7 @@
 src/lib/ecore_sdl/Makefile
 src/lib/ecore_evas/Makefile
 src/lib/ecore_con/Makefile
+src/lib/ecore_download/Makefile
 src/lib/ecore_ipc/Makefile
 src/lib/ecore_txt/Makefile
 src/lib/ecore_config/Makefile
@@ -866,7 +895,8 @@
 echo "Optional Modules:"
 echo
 echo "  Ecore_Job....................: $have_ecore_job"
-echo "  Ecore_Con....................: $have_ecore_con (OpenSSL: $use_openssl)"
+echo "  Ecore_Con....................: $have_ecore_con (OpenSSL: $use_openssl) (CURL: $use_curl)"
+echo "  Ecore_Download...............: $have_ecore_download"
 echo "  Ecore_Txt....................: $have_ecore_txt"
 if test "x$have_ecore_x_xcb" = "xyes" ; then
 echo "  Ecore_X (XCB backend)........: $have_ecore_x_xcb (Xprint: $have_ecore_x_xcb_xprint) (Xinerama: $have_ecore_x_xcb_xinerama) (Xrandr: $have_ecore_x_xcb_randr) (Xscreensaver: $have_ecore_x_xcb_screensaver) (Xshape: $have_ecore_x_xcb_shape) (Xsync: $have_ecore_x_xcb_sync) (Xrender: $have_ecore_x_xcb_render) (Xfixes: $have_ecore_x_xcb_xfixes) (Xdamage: $have_ecore_x_xcb_damage) (Xdpms: $have_ecore_x_xcb_dpms)"
diff -Nrau -X exclude.cvs e17-clean/libs/ecore/ecore-download.pc.in e17-dev/libs/ecore/ecore-download.pc.in
--- e17-clean/libs/ecore/ecore-download.pc.in	1970-01-01 01:00:00.000000000 +0100
+++ e17-dev/libs/ecore/ecore-download.pc.in	2007-08-10 19:03:54.000000000 +0200
@@ -0,0 +1,11 @@
[EMAIL PROTECTED]@
[EMAIL PROTECTED]@
[EMAIL PROTECTED]@
[EMAIL PROTECTED]@
+
+Name: ecore-download
+Description: E core library, Download module
+Requires: ecore @requirements_ecore_download@
+Version: @VERSION@
+Libs: -L${libdir} -lecore_download
+Cflags: -I${includedir}
diff -Nrau -X exclude.cvs e17-clean/libs/ecore/Makefile.am e17-dev/libs/ecore/Makefile.am
--- e17-clean/libs/ecore/Makefile.am	2007-07-16 20:17:59.000000000 +0200
+++ e17-dev/libs/ecore/Makefile.am	2007-08-10 20:08:40.000000000 +0200
@@ -15,6 +15,7 @@
 		       ecore-desktop.pc \
 		       ecore-directfb.pc\
 		       ecore-evas.pc \
+		       ecore-download.pc \
 		       ecore-fb.pc \
 		       ecore-file.pc \
 		       ecore-ipc.pc \
@@ -41,6 +42,7 @@
 	     ecore-txt.pc.in \
 	     ecore-x.pc.in \
 	     ecore-sdl.pc.in \
+	     ecore-download.pc.in \
 	     ecore.spec.in ecore.spec \
 	     debian/changelog \
 	     debian/changelog.in \
@@ -61,6 +63,10 @@
 	     debian/libecore0.install \
 	     debian/rules
 
+if BUILD_ECORE_DOWNLOAD
+pdownload = ecore-download.pc
+endif
+
 if BUILD_ECORE_CON
 pcon = ecore-con.pc
 endif
@@ -116,4 +122,4 @@
 pkgconfigdir = $(libdir)/pkgconfig
 pkgconfig_DATA = \
 	ecore.pc $(pcon) $(pconfig) $(pdfb) $(pevas) \
-	$(pfb) $(pfile) $(pdesktop) $(pipc) $(pjob) $(ptxt) $(px) $(psdl)
+	$(pfb) $(pfile) $(pdesktop) $(pipc) $(pjob) $(ptxt) $(px) $(psdl) $(pdownload)
diff -Nrau -X exclude.cvs e17-clean/libs/ecore/src/lib/ecore/ecore_private.h e17-dev/libs/ecore/src/lib/ecore/ecore_private.h
--- e17-clean/libs/ecore/src/lib/ecore/ecore_private.h	2007-07-06 11:58:55.000000000 +0200
+++ e17-dev/libs/ecore/src/lib/ecore/ecore_private.h	2007-08-09 15:41:53.000000000 +0200
@@ -88,6 +88,8 @@
 #define ECORE_MAGIC_EVENT_FILTER    0xf78218ff
 #define ECORE_MAGIC_EVENT           0xf77119fe
 #define ECORE_MAGIC_ANIMATOR        0xf7643ea5
+#define ECORE_MAGIC_DOWNLOAD_FILES  0xf7742cb5
+#define ECORE_MAGIC_DOWNLOAD_DIR    0xf775cb42
 
 #define ECORE_MAGIC                 Ecore_Magic  __magic
 
diff -Nrau -X exclude.cvs e17-clean/libs/ecore/src/lib/ecore_download/ecore_download.c e17-dev/libs/ecore/src/lib/ecore_download/ecore_download.c
--- e17-clean/libs/ecore/src/lib/ecore_download/ecore_download.c	1970-01-01 01:00:00.000000000 +0100
+++ e17-dev/libs/ecore/src/lib/ecore_download/ecore_download.c	2007-09-14 20:54:56.000000000 +0200
@@ -0,0 +1,530 @@
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <unistd.h>
+#include <dirent.h>
+#include <stdlib.h>
+#include <curl/curl.h>
+
+#include "Ecore.h"
+#include "ecore_private.h"
+#include "Ecore_Con.h"
+#include "Ecore_Data.h"
+#include "Ecore_Download.h"
+
+struct _Ecore_Download_Dir
+{
+  ECORE_MAGIC;
+
+  const char            *files_directory;
+  const char            *temp_directory;
+  const char            *prefix;
+
+  const void            *data;
+
+  Ecore_List            *download;
+};
+
+struct _Ecore_Download_File
+{
+  ECORE_MAGIC;
+
+  Ecore_Download_Dir    *dir;
+
+  Ecore_Con_Url         *url_con;
+  const char            *url;
+
+  const char            *file;
+  time_t                 tm;
+
+  const char            *temp;
+  int                    fd;
+
+  const void            *data;
+
+  int                    active : 1;
+  int                    updated : 1;
+};
+
+int ECORE_DOWNLOAD_EVENT_CANCEL = 0;
+int ECORE_DOWNLOAD_EVENT_COMPLETE = 0;
+int ECORE_DOWNLOAD_EVENT_PROGRESS = 0;
+
+static Ecore_Event_Handler      *ed_url_data = NULL;
+static Ecore_Event_Handler      *ed_url_complete = NULL;
+static Ecore_Event_Handler      *ed_url_progress_download = NULL;
+
+static int
+_ecore_download_url_data_cb(void *data, int type, void *event)
+{
+   Ecore_Con_Event_Url_Data     *e;
+   Ecore_Download_File          *edf;
+
+   e = event;
+
+   edf = ecore_con_url_data_get(e->url_con);
+
+   if (!ECORE_MAGIC_CHECK(edf, ECORE_MAGIC_DOWNLOAD_FILES)) return 1;
+
+   if (edf->fd != -1)
+     {
+        edf->updated = 1;
+        write(edf->fd, e->data, e->size);
+     }
+
+   return 0;
+}
+
+static Ecore_Download_Event_Complete*
+_ecore_download_event_complete_new(Ecore_Download_File *edf, int status)
+{
+   Ecore_Download_Event_Complete   *edec;
+
+   edec = calloc(1, sizeof(Ecore_Download_Event_Complete) + strlen(edf->file) + 1);
+   if (edec == NULL) return NULL;
+
+   edec->edf = edf;
+   edec->status = status;
+   edec->file = (const char*)((Ecore_Download_Event_Complete*) (edec + 1));
+   memcpy((char*)edec->file, edf->file, strlen(edf->file) + 1);
+
+   edf->fd = -1;
+   edf->active = 0;
+
+   return edec;
+}
+
+static int
+_ecore_download_url_complete_cb(void *data, int type, void *event)
+{
+   Ecore_Download_Event_Cancel  *edec;
+   Ecore_Con_Event_Url_Complete *e;
+   Ecore_Download_File          *edf;
+
+   e = event;
+
+   edf = ecore_con_url_data_get(e->url_con);
+
+   if (!ECORE_MAGIC_CHECK(edf, ECORE_MAGIC_DOWNLOAD_FILES)) return 1;
+
+   /* Restart download. */
+   if (e->status == 304)
+     {
+        unlink(edf->temp);
+        if (edf->fd >= 0)
+          close(edf->fd);
+
+        ecore_event_add(ECORE_DOWNLOAD_EVENT_COMPLETE, _ecore_download_event_complete_new(edf, e->status), NULL, NULL);
+
+        return 0;
+     }
+
+   /* File download ok. */
+   if (e->status == 200)
+     {
+        /* File update. */
+        if (edf->updated != 0)
+          {
+             unlink(edf->file);
+             if (rename(edf->temp, edf->file) != 0)
+               e->status = -200;
+          }
+        else
+          {
+             unlink(edf->temp);
+          }
+
+        if (edf->fd >= 0)
+          close(edf->fd);
+
+        ecore_event_add(ECORE_DOWNLOAD_EVENT_COMPLETE, _ecore_download_event_complete_new(edf, e->status), NULL, NULL);
+
+        return 0;
+     }
+
+   if (edf->fd != -1)
+     {
+        close(edf->fd);
+        edf->fd = -1;
+        unlink(edf->temp);
+     }
+
+   snprintf((char*)edf->temp,
+            strlen(edf->dir->temp_directory) + strlen(edf->dir->prefix) + 5,
+            "%s/%sXXXXXX",
+            edf->dir->temp_directory,
+            edf->dir->prefix);
+   edf->fd = mkstemp((char*)edf->temp);
+
+   edf->active = 0;
+
+   edec = calloc(1, sizeof(Ecore_Download_Event_Cancel) + strlen(edf->url) + 1);
+   if (edec == NULL) return 0;
+
+   edec->edf = edf;
+   edec->status = e->status;
+   edec->url = (const char*) ((Ecore_Download_Event_Cancel*) (edec + 1));
+   memcpy((char*)edec->url, edf->url, strlen(edf->url) + 1);
+
+   ecore_event_add(ECORE_DOWNLOAD_EVENT_CANCEL, edec, NULL, NULL);
+
+   return 0;
+}
+
+static int
+_ecore_download_url_progress_download_cb(void *data, int type, void *event)
+{
+   Ecore_Con_Event_Url_Progress_Download        *e;
+   Ecore_Download_Event_Progress                *edep;
+   Ecore_Download_File                          *edf;
+
+   e = event;
+   edf = ecore_con_url_data_get(e->url_con);
+
+   if (!ECORE_MAGIC_CHECK(edf, ECORE_MAGIC_DOWNLOAD_FILES)) return 0;
+
+   edep = calloc(1, sizeof(Ecore_Download_Event_Progress) + strlen(edf->url) + 1);
+   if (edep == NULL) return 0;
+
+   edep->edf = edf;
+   edep->total = e->total;
+   edep->now = e->now;
+   edep->url = (const char*) ((Ecore_Download_Event_Progress*) (edep + 1));
+   memcpy((char*)edep->url, edf->url, strlen(edf->url) + 1);
+
+   ecore_event_add(ECORE_DOWNLOAD_EVENT_PROGRESS, edep, NULL, NULL);
+
+   return 1;
+}
+
+int
+ecore_download_init(void)
+{
+   ecore_init();
+   ecore_con_url_init();
+
+   if (!ECORE_DOWNLOAD_EVENT_COMPLETE)
+     {
+        ECORE_DOWNLOAD_EVENT_PROGRESS = ecore_event_type_new();
+        ECORE_DOWNLOAD_EVENT_COMPLETE = ecore_event_type_new();
+        ECORE_DOWNLOAD_EVENT_CANCEL = ecore_event_type_new();
+
+        ed_url_data = ecore_event_handler_add(ECORE_CON_EVENT_URL_DATA, _ecore_download_url_data_cb, NULL);
+        ed_url_complete = ecore_event_handler_add(ECORE_CON_EVENT_URL_COMPLETE, _ecore_download_url_complete_cb, NULL);
+        ed_url_progress_download = ecore_event_handler_add(ECORE_CON_EVENT_URL_PROGRESS_DOWNLOAD, _ecore_download_url_progress_download_cb, NULL);
+     }
+
+   return 1;
+}
+
+int
+ecore_download_shutdown(void)
+{
+   ecore_con_url_shutdown();
+   ecore_shutdown();
+
+   return 1;
+}
+
+static int
+_ecore_download_directory_cleanup(const char *temp, const char *prefix)
+{
+   char                 *todel = NULL;
+   DIR                  *dr;
+   struct dirent        *dirent;
+
+   dr = opendir(temp);
+   if (dr == NULL)
+     return -1;
+
+   while ((dirent = readdir(dr)) != NULL)
+     {
+        if (strncmp(dirent->d_name, prefix, strlen(prefix)) == 0)
+          {
+             int        length;
+
+             length = strlen(dirent->d_name) + strlen(temp) + 2;
+             todel = realloc(todel, sizeof(char) * length);
+
+             if (todel == NULL)
+               return -1;
+
+             snprintf((char*)todel, length, "%s/%s", temp, dirent->d_name);
+
+             unlink(todel);
+          }
+     }
+   IF_FREE(todel);
+
+   if (closedir(dr) != 0)
+     return -1;
+
+   return 0;
+}
+
+Ecore_Download_Dir*
+ecore_download_directory_new(const char *files, const char *temp, const char *prefix)
+{
+   Ecore_Download_Dir   *edd;
+   struct stat           st;
+
+   if (prefix == NULL)
+     return NULL;
+
+   if (stat(files, &st) != 0)
+     return NULL;
+
+   if (!S_ISDIR(st.st_mode))
+     return NULL;
+
+   if (stat(temp, &st) != 0)
+     return NULL;
+
+   if (!S_ISDIR(st.st_mode))
+     return NULL;
+
+   /* On crach some data could have survived, clean them all. */
+   if (_ecore_download_directory_cleanup(temp, prefix) != 0)
+     return NULL;
+
+   edd = calloc(1, sizeof(Ecore_Download_Dir) + strlen(files) + strlen(temp) + strlen(prefix) + 3);
+   if (edd == NULL)
+     return NULL;
+
+   edd->files_directory = (const char*) ((Ecore_Download_Dir*) (edd + 1));
+   edd->temp_directory = edd->files_directory + strlen(files) + 1;
+   edd->prefix = edd->temp_directory + strlen(temp) + 1;
+
+   memcpy((char*)edd->files_directory, files, strlen(files) + 1);
+   memcpy((char*)edd->temp_directory, temp, strlen(temp) + 1);
+   memcpy((char*)edd->prefix, prefix, strlen(prefix) + 1);
+
+   edd->download = ecore_list_new();
+
+   ECORE_MAGIC_SET(edd, ECORE_MAGIC_DOWNLOAD_DIR);
+   return edd;
+}
+
+static void
+_ecore_destroy_cb(void *value, void *user_data __UNUSED__)
+{
+   ecore_download_file_destroy(value);
+}
+
+void
+ecore_download_directory_destroy(Ecore_Download_Dir* dir)
+{
+   if (!ECORE_MAGIC_CHECK(dir, ECORE_MAGIC_DOWNLOAD_DIR))
+     {
+        ECORE_MAGIC_FAIL(dir, ECORE_MAGIC_DOWNLOAD_DIR, "ecore_download_directory_destroy");
+        return ;
+     }
+
+   ecore_list_for_each(dir->download, _ecore_destroy_cb, NULL);
+
+   /* Just in case, clean temp dir. */
+   _ecore_download_directory_cleanup(dir->temp_directory, dir->prefix);
+
+   ECORE_MAGIC_SET(dir, ECORE_MAGIC_NONE);
+   free(dir);
+}
+
+void*
+ecore_download_directory_data_set(Ecore_Download_Dir *dir, const void *data)
+{
+   void *old;
+
+   if (!ECORE_MAGIC_CHECK(dir, ECORE_MAGIC_DOWNLOAD_DIR))
+     {
+        ECORE_MAGIC_FAIL(dir, ECORE_MAGIC_DOWNLOAD_DIR, "ecore_download_directory_data_set");
+        return NULL;
+     }
+
+   old = (void*) dir->data;
+   dir->data = data;
+
+   return old;
+}
+
+void*
+ecore_download_directory_data_get(Ecore_Download_Dir *dir)
+{
+   if (!ECORE_MAGIC_CHECK(dir, ECORE_MAGIC_DOWNLOAD_DIR))
+     {
+        ECORE_MAGIC_FAIL(dir, ECORE_MAGIC_DOWNLOAD_DIR, "ecore_download_directory_data_get");
+        return NULL;
+     }
+
+   return (void*) dir->data;
+}
+
+Ecore_Download_File*
+ecore_download_file_add(Ecore_Download_Dir* dir, const char* file, const char* url)
+{
+   Ecore_Download_File  *edf = NULL;
+   Ecore_Con_Url        *ecu;
+   int                   length_temp;
+   int                   length_file;
+   struct stat           st;
+
+   if (!ECORE_MAGIC_CHECK(dir, ECORE_MAGIC_DOWNLOAD_DIR))
+     {
+        ECORE_MAGIC_FAIL(dir, ECORE_MAGIC_DOWNLOAD_DIR, "ecore_download_file_add");
+        return NULL;
+     }
+
+   ecu = ecore_con_url_new(url);
+   if (ecu == NULL) goto on_error;
+
+   length_temp = strlen(dir->temp_directory) + strlen(dir->prefix) + 8;
+   length_file = strlen(dir->files_directory) + strlen(file) + 2;
+   edf = calloc(1, sizeof (Ecore_Download_File)
+                + length_file
+                + strlen(url) + 1
+                + length_temp);
+   if (edf == NULL) goto on_error;
+
+   edf->url_con = ecu;
+   edf->dir = dir;
+   edf->file = (const char*) ((Ecore_Download_File*)(edf + 1));
+   edf->url = edf->file + length_file + 1;
+   edf->temp = edf->url + strlen(url);
+
+   memcpy((char*)edf->file, file, strlen(file) + 1);
+   memcpy((char*)edf->url, url, strlen(url) + 1);
+
+   snprintf((char*)edf->temp, length_temp, "%s/%sXXXXXX", dir->temp_directory, dir->prefix);
+   edf->fd = mkstemp((char*)edf->temp);
+   if (edf->fd < 0) goto on_error;
+
+   snprintf((char*)edf->file, length_file, "%s/%s", dir->files_directory, file);
+   if (stat(edf->file, &st) == 0)
+     edf->tm = st.st_mtime;
+
+   ecore_list_append(dir->download, edf);
+   ecore_con_url_data_set(ecu, edf);
+
+   ECORE_MAGIC_SET(edf, ECORE_MAGIC_DOWNLOAD_FILES);
+   return edf;
+
+ on_error:
+   if (ecu != NULL) ecore_con_url_destroy(ecu);
+   if (edf != NULL) free(edf);
+   return NULL;
+}
+
+int
+ecore_download_file_start(Ecore_Download_File* edf)
+{
+   if (!ECORE_MAGIC_CHECK(edf, ECORE_MAGIC_DOWNLOAD_FILES))
+     {
+        ECORE_MAGIC_FAIL(edf, ECORE_MAGIC_DOWNLOAD_FILES, "ecore_download_file_start");
+        return -1;
+     }
+
+   if (edf->active)
+     return 0;
+
+   edf->active = 1;
+
+   if (edf->tm != 0)
+     ecore_con_url_time(edf->url_con, ECORE_CON_URL_TIME_IFMODSINCE, edf->tm);
+
+   return ecore_con_url_send(edf->url_con, NULL, 0, NULL);
+}
+
+int
+ecore_download_file_stop(Ecore_Download_File* edf)
+{
+   if (!ECORE_MAGIC_CHECK(edf, ECORE_MAGIC_DOWNLOAD_FILES))
+     {
+        ECORE_MAGIC_FAIL(edf, ECORE_MAGIC_DOWNLOAD_FILES, "ecore_download_file_stop");
+        return -1;
+     }
+
+   if (!edf->active) return 0;
+
+   ecore_con_url_destroy(edf->url_con);
+   edf->url_con = ecore_con_url_new(edf->url);
+
+   if (edf->fd != -1)
+     {
+        close(edf->fd);
+        unlink(edf->temp);
+     }
+
+   snprintf((char*)edf->temp,
+            strlen(edf->dir->temp_directory) + strlen(edf->dir->prefix) + 5,
+            "%s/%sXXXXXX",
+            edf->dir->temp_directory,
+            edf->dir->prefix);
+   edf->fd = mkstemp((char*)edf->temp);
+   if (edf->fd < 0) goto on_error;
+
+   edf->active = 0;
+
+   return 0;
+
+ on_error:
+   /* FIXME: edf is now completely useless. */
+   return -1;
+}
+
+void
+ecore_download_file_destroy(Ecore_Download_File* edf)
+{
+   Ecore_Download_File* lookup;
+
+   if (!ECORE_MAGIC_CHECK(edf, ECORE_MAGIC_DOWNLOAD_FILES))
+     {
+        ECORE_MAGIC_FAIL(edf, ECORE_MAGIC_DOWNLOAD_FILES, "ecore_download_file_destroy");
+        return ;
+     }
+
+   ecore_con_url_destroy(edf->url_con);
+   edf->url_con = NULL;
+
+   if (edf->fd != -1)
+     {
+        close(edf->fd);
+        unlink(edf->temp);
+     }
+
+   for (lookup = ecore_list_first_goto(edf->dir->download);
+        lookup != NULL && lookup != edf;
+        lookup = ecore_list_next(edf->dir->download))
+     ;
+
+   if (lookup == edf)
+     ecore_list_remove(edf->dir->download);
+
+   ECORE_MAGIC_SET(edf, ECORE_MAGIC_NONE);
+}
+
+void*
+ecore_download_file_data_set(Ecore_Download_File *edf, const void *data)
+{
+   void*        old;
+
+   if (!ECORE_MAGIC_CHECK(edf, ECORE_MAGIC_DOWNLOAD_FILES))
+     {
+        ECORE_MAGIC_FAIL(edf, ECORE_MAGIC_DOWNLOAD_FILES, "ecore_download_file_data_set");
+        return NULL;
+     }
+
+   old = (void*) edf->data;
+   edf->data = data;
+
+   return old;
+}
+
+void*
+ecore_download_file_data_get(Ecore_Download_File *edf)
+{
+   if (!ECORE_MAGIC_CHECK(edf, ECORE_MAGIC_DOWNLOAD_FILES))
+     {
+        ECORE_MAGIC_FAIL(edf, ECORE_MAGIC_DOWNLOAD_FILES, "ecore_download_file_data_get");
+        return NULL;
+     }
+
+   return (void*) edf->data;
+}
diff -Nrau -X exclude.cvs e17-clean/libs/ecore/src/lib/ecore_download/Ecore_Download.h e17-dev/libs/ecore/src/lib/ecore_download/Ecore_Download.h
--- e17-clean/libs/ecore/src/lib/ecore_download/Ecore_Download.h	1970-01-01 01:00:00.000000000 +0100
+++ e17-dev/libs/ecore/src/lib/ecore_download/Ecore_Download.h	2007-09-13 16:08:01.000000000 +0200
@@ -0,0 +1,60 @@
+#ifndef         ECORE_DOWNLOAD_H__
+# define        ECORE_DOWNLOAD_H__
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+  typedef struct _Ecore_Download_Event_Complete   Ecore_Download_Event_Complete;
+  typedef struct _Ecore_Download_Event_Cancel     Ecore_Download_Event_Cancel;
+  typedef struct _Ecore_Download_Event_Progress   Ecore_Download_Event_Progress;
+
+  typedef struct _Ecore_Download_File             Ecore_Download_File;
+  typedef struct _Ecore_Download_Dir              Ecore_Download_Dir;
+
+  struct _Ecore_Download_Event_Complete
+  {
+    Ecore_Download_File   *edf;
+    const char            *file;
+    int                    status;
+  };
+
+  struct _Ecore_Download_Event_Cancel
+  {
+    Ecore_Download_File   *edf;
+    const char            *url;
+    int                    status;
+  };
+
+  struct _Ecore_Download_Event_Progress
+  {
+    Ecore_Download_File   *edf;
+    const char            *url;
+    double                 total;
+    double                 now;
+  };
+
+  EAPI extern int ECORE_DOWNLOAD_EVENT_CANCEL;
+  EAPI extern int ECORE_DOWNLOAD_EVENT_COMPLETE;
+  EAPI extern int ECORE_DOWNLOAD_EVENT_PROGRESS;
+
+  EAPI int                       ecore_download_init(void);
+  EAPI int                       ecore_download_shutdown(void);
+
+  EAPI Ecore_Download_Dir       *ecore_download_directory_new(const char *files, const char *temp, const char *prefix);
+  EAPI void                      ecore_download_directory_destroy(Ecore_Download_Dir *dir);
+  EAPI void                     *ecore_download_directory_data_set(Ecore_Download_Dir *dir, const void *data);
+  EAPI void                     *ecore_download_directory_data_get(Ecore_Download_Dir *dir);
+
+  EAPI Ecore_Download_File      *ecore_download_file_add(Ecore_Download_Dir *dir, const char *file, const char *url);
+  EAPI int                       ecore_download_file_start(Ecore_Download_File *edf);
+  EAPI int                       ecore_download_file_stop(Ecore_Download_File *edf);
+  EAPI void                      ecore_download_file_destroy(Ecore_Download_File *edf);
+  EAPI void                     *ecore_download_file_data_set(Ecore_Download_File *edf, const void *data);
+  EAPI void                     *ecore_download_file_data_get(Ecore_Download_File *edf);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif       /* ECORE_DOWNLOAD_H__ */
diff -Nrau -X exclude.cvs e17-clean/libs/ecore/src/lib/ecore_download/Makefile.am e17-dev/libs/ecore/src/lib/ecore_download/Makefile.am
--- e17-clean/libs/ecore/src/lib/ecore_download/Makefile.am	1970-01-01 01:00:00.000000000 +0100
+++ e17-dev/libs/ecore/src/lib/ecore_download/Makefile.am	2007-08-10 14:04:20.000000000 +0200
@@ -0,0 +1,35 @@
+MAINTAINERCLEANFILES = Makefile.in
+
+INCLUDES = \
+-I$(top_builddir)/src/lib/ecore \
+-I$(top_builddir)/src/lib/ecore_con \
+-I$(top_builddir)/src/lib/ecore_download \
+-I$(top_srcdir)/src/lib/ecore \
+-I$(top_srcdir)/src/lib/ecore_con \
+-I$(top_srcdir)/src/lib/ecore_download
+
+libecore_download_la_LDFLAGS = -version-info 1:0:0 \
+-L$(top_builddir)/src/lib/ecore/.libs
+
+if BUILD_ECORE_DOWNLOAD
+
+lib_LTLIBRARIES = libecore_download.la
+include_HEADERS = \
+Ecore_Download.h
+
+libecore_download_la_SOURCES = \
+ecore_download.c
+
+libecore_download_la_LIBADD = \
+$(top_builddir)/src/lib/ecore/libecore.la \
+$(top_builddir)/src/lib/ecore_con/libecore_con.la
+
+libecore_download_la_DEPENDENCIES = \
+$(top_builddir)/src/lib/ecore/libecore.la \
+$(top_builddir)/src/lib/ecore_con/libecore_con.la
+
+endif
+
+EXTRA_DIST = \
+ecore_download.c \
+Ecore_Download.h
diff -Nrau -X exclude.cvs e17-clean/libs/ecore/src/lib/Makefile.am e17-dev/libs/ecore/src/lib/Makefile.am
--- e17-clean/libs/ecore/src/lib/Makefile.am	2007-07-16 20:17:59.000000000 +0200
+++ e17-dev/libs/ecore/src/lib/Makefile.am	2007-08-10 13:45:50.000000000 +0200
@@ -12,4 +12,5 @@
 ecore_evas \
 ecore_config \
 ecore_file \
-ecore_desktop
+ecore_desktop \
+ecore_download
-------------------------------------------------------------------------
This SF.net email is sponsored by: Microsoft
Defy all challenges. Microsoft(R) Visual Studio 2005.
http://clk.atdmt.com/MRT/go/vse0120000070mrt/direct/01/
_______________________________________________
enlightenment-devel mailing list
enlightenment-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/enlightenment-devel

Reply via email to