예제 #1
0
static uulist *
UU_smparts_r (uulist *addit, int pass)
{
  uulist *iter = UUGlobalFileList;
  uufile *fiter, *dest, *temp;
  int count, flag, a, b;

  while (iter) {
    if ((iter->state & UUFILE_OK) || iter->uudet == 0) {
      iter = iter->NEXT;
      continue;
    }
    if (iter == addit) {
      iter = iter->NEXT;
      continue;
    }
    if ((iter->begin && addit->begin) || (iter->end && addit->end) ||
	(iter->uudet != addit->uudet)) {
      iter = iter->NEXT;
      continue;
    }
    if ((a = UUSMPKnownExt (addit->subfname)) != -1 &&
        (b = UUSMPKnownExt (iter->subfname))  != -1)
      if (a != b) {
        iter = iter->NEXT;
        continue;
      }

    flag  = count = 0;
    fiter = iter->thisfile;
    temp  = addit->thisfile;
    dest  = NULL;

    while (temp) {
      if (!(temp->data->uudet)) {
	temp = temp->NEXT;
	continue;
      }

      while (fiter && fiter->partno < temp->partno) {
        dest  = fiter;
        fiter = fiter->NEXT;
      }
      if (fiter && fiter->partno == temp->partno) {
        flag = 0;
        break;
      }
      else {
	flag   = 1;
        count += ((dest)  ? temp->partno - dest->partno - 1 : 0) +
                 ((fiter) ? fiter->partno - temp->partno - 1 : 0);
      }

      temp = temp->NEXT;
    }
    if (flag == 0 ||
        (pass == 0 && count > 0) ||
        (pass == 1 && count > 5)) {
      iter = iter->NEXT;
      continue;
    }

    dest  = iter->thisfile;
    fiter = addit->thisfile;

    if (iter->filename == NULL && addit->filename != NULL)
      iter->filename = _FP_strdup (addit->filename);

    if (addit->begin) iter->begin = 1;
    if (addit->end)   iter->end   = 1;

    if (addit->mode != 0 && iter->mode == 0)
      iter->mode = addit->mode;

    while (fiter) {
      flag = 0;

      if (fiter->partno == iter->thisfile->partno ||
	  (dest->NEXT != NULL && fiter->partno == dest->NEXT->partno)) {
	temp           = fiter->NEXT;
	fiter->NEXT    = NULL;

	UUkillfile (fiter);

	addit->thisfile= temp;
	fiter          = temp;
	continue;
      }
      if (fiter->partno < iter->thisfile->partno) {
	temp           = fiter->NEXT;
	fiter->NEXT    = iter->thisfile;
	iter->thisfile = fiter;
	dest           = fiter;
	addit->thisfile= temp;
	fiter          = temp;
      }
      else if (dest->NEXT == NULL || fiter->partno < dest->NEXT->partno) {
	temp           = fiter->NEXT;
	fiter->NEXT    = dest->NEXT;
	dest->NEXT     = fiter;
	addit->thisfile= temp;
	fiter          = temp;
      }
      else {
	dest = dest->NEXT;
      }
    }
    break;
  }
  return iter;
}
예제 #2
0
uufile *
UUPreProcessPart (fileread *data, int *ret)
{
  char *where, *whend, temp[80], *ptr, *p2;
  uufile *result;

  if ((result = (uufile *) malloc (sizeof (uufile))) == NULL) {
    UUMessage (uucheck_id, __LINE__, UUMSG_ERROR,
	       uustring (S_OUT_OF_MEMORY), sizeof (uufile));
    *ret = UURET_NOMEM;
    return NULL;
  }
  memset (result, 0, sizeof (uufile));

  if (data->partno) {
    where = whend  = NULL;
    result->partno = data->partno;
  }
  else if (uu_dumbness) {
    result->partno = -1;
    where = whend  = NULL;
  }
  else if ((result->partno=UUGetPartNo(data->subject,&where,&whend)) == -2) {
    *ret = UURET_NODATA;
    UUkillfile (result);
    return NULL;
  }

  if (data->filename != NULL) {
    if ((result->filename = _FP_strdup (data->filename)) == NULL) {
      UUMessage (uucheck_id, __LINE__, UUMSG_ERROR,
		 uustring (S_OUT_OF_MEMORY),
		 strlen (data->filename)+1);
      *ret = UURET_NOMEM;
      UUkillfile (result);
      return NULL;
    }
  }
  else
    result->filename = NULL;

  if (uu_dumbness <= 1)
    result->subfname = UUGetFileName (data->subject, where, whend);
  else
    result->subfname = NULL;

  result->mimeid   = _FP_strdup (data->mimeid);
  result->mimetype = _FP_strdup (data->mimetype);

  if (result->partno == -1 && 
      (data->uudet == PT_ENCODED || data->uudet == QP_ENCODED))
    result->partno = 1;

  if (data->flags & FL_SINGLE) {
    /*
     * Don't touch this part. But it should really have a filename
     */
    if (result->filename == NULL) {
      sprintf (temp, "%s.%03d", nofname, ++nofnum);
      result->filename = _FP_strdup (temp);
    }
    if (result->subfname == NULL)
      result->subfname = _FP_strdup (result->filename);

    if (result->filename == NULL || 
	result->subfname == NULL) {
      UUMessage (uucheck_id, __LINE__, UUMSG_ERROR,
		 uustring (S_OUT_OF_MEMORY),
		 (result->filename==NULL)?
		 (strlen(temp)+1):(strlen(result->filename)+1));
      *ret = UURET_NOMEM;
      UUkillfile(result);
      return NULL;
    }
    if (result->partno == -1)
      result->partno = 1;
  }
  else if (result->subfname == NULL && data->uudet &&
      (data->begin || result->partno == 1 || 
       (!uu_dumbness && result->partno == -1 && 
	(data->subject != NULL || result->filename != NULL)))) {
    /*
     * If it's the first part of something and has some valid data, but
     * no subject or anything, initialize lastvalid
     */
    /*
     * in this case, it really _should_ have a filename somewhere
     */
    if (result->filename != NULL)
      result->subfname = _FP_strdup (result->filename);
    else { /* if not, escape to UNKNOWN. We need to fill subfname */
      sprintf (temp, "%s.%03d", nofname, ++nofnum);
      result->subfname = _FP_strdup (temp);
    }
    /*
     * in case the strdup failed
     */
    if (result->subfname == NULL) {
      UUMessage (uucheck_id, __LINE__, UUMSG_ERROR,
		 uustring (S_OUT_OF_MEMORY),
		 (result->filename)?
		 (strlen(result->filename)+1):(strlen(temp)+1));
      *ret = UURET_NOMEM;
      UUkillfile (result);
      return NULL;
    }
    /*
     * if it's also got an 'end', or is the last part in a MIME-Mail,
     * then don't set lastvalid
     */
    if (!data->end && (!data->partno || data->partno != data->maxpno)) {
      /*
       * initialize lastvalid
       */
      lastvalid = 1;
      lastenc   = data->uudet;
      lastpart  = result->partno = 1;
      _FP_strncpy (uucheck_lastname, result->subfname, 256);
    }
    else
      result->partno = 1;
  }
  else if (result->subfname == NULL && data->uudet && data->mimeid) {
    /*
     * if it's got a file name, use it. Else use the mime-id for identifying
     * this part, and hope there's no other files encoded in the same message
     * under the same id.
     */
    if (result->filename)
      result->subfname = _FP_strdup (result->filename);
    else
      result->subfname = _FP_strdup (result->mimeid);
  }
  else if (result->subfname == NULL && data->uudet) {
    /*
     * ff we have lastvalid, use it. Make an exception for
     * Base64-encoded files.
     */
    if (data->uudet == B64ENCODED) {
      /*
       * Assume it's the first part. I wonder why it's got no part number?
       */
      if (result->filename != NULL)
        result->subfname = _FP_strdup (result->filename);
      else { /* if not, escape to UNKNOWN. We need to fill subfname */
        sprintf (temp, "%s.%03d", nofname, ++nofnum);
        result->subfname = _FP_strdup (temp);
      }
      if (result->subfname == NULL) {
	UUMessage (uucheck_id, __LINE__, UUMSG_ERROR,
		   uustring (S_OUT_OF_MEMORY),
		   (result->filename)?
		   (strlen(result->filename)+1):(strlen(temp)+1));
	*ret = UURET_NOMEM;
	UUkillfile (result);
        return NULL;
      }
      lastvalid = 0;
    }
    else if (lastvalid && data->uudet == lastenc && result->partno == -1) {
      result->subfname = _FP_strdup (uucheck_lastname);
      result->partno   = ++lastpart;

      /*
       * if it's the last part, invalidate lastvalid
       */
      if (data->end || (data->partno && data->partno == data->maxpno))
	lastvalid = 0;
    }
    else if (data->partno != -1 && result->filename) {
      result->subfname = _FP_strdup (result->filename);
    }
    else { 
      /* 
       * it's got no info, it's got no begin, and we don't know anything
       * about this part. Let's forget all about it.
       */
      *ret = UURET_NODATA;
      UUkillfile (result);
      return NULL;
    }
  }
  else if (result->subfname == NULL && result->partno == -1) {
    /*
     * This, too, is a part without any useful information that we
     * should forget about.
     */
    *ret = UURET_NODATA;
    UUkillfile (result);
    return NULL;
  }
  else if (result->subfname == NULL) {
    /*
     * This is a part without useful subject name, a valid part number
     * but no encoded data. It *could* be the zeroeth part of something,
     * but we don't care here. Just forget it.
     */
    *ret = UURET_NODATA;
    UUkillfile (result);
    return NULL;
  }

  /*
   * now, handle some cases where we have a useful subject but no
   * useful part number
   */

  if (result->partno == -1 && data->begin) {
    /*
     * hmm, this is reason enough to initialize lastvalid, at least 
     * if we have no end
     */
    if (!data->end) {
      _FP_strncpy (uucheck_lastname, result->subfname, 256);
      result->partno = lastpart = 1;
      lastenc = data->uudet;
      lastvalid = 1;
    }
    else
      result->partno = 1;
  }
  else if (result->partno == -1 && data->uudet) {
    if (lastvalid && _FP_stricmp (uucheck_lastname, result->subfname) == 0) {
      /*
       * if the subject filename is the same as last time, use part no
       * of lastvalid. If at end, invalidate lastvalid
       */
      result->partno = ++lastpart;

      if (data->end)
	lastvalid = 0;
    }
    else {
      /*
       * data but no part no. It's something UUInsertPartToList() should
       * handle
       */
      goto skipcheck;
    }
  }
  else if (result->partno == -1) {
    /*
     * it's got no data, so why should we need this one anyway?
     */
    *ret = UURET_NODATA;
    UUkillfile (result);
    return NULL;
  }

  /*
   * at this point, the part should have a valid subfname and a valid
   * part number. If it doesn't, then fail.
   */
  if (result->subfname == NULL || result->partno == -1) {
    *ret = UURET_NODATA;
    UUkillfile (result);
    return NULL;
  }

 skipcheck:

  if (result->filename) {
    if (*(ptr = _FP_cutdir (result->filename))) {
      p2 = _FP_strdup (ptr);
      _FP_free (result->filename);
      result->filename = p2;
    }
  }

  result->data = data;
  result->NEXT = NULL;

  *ret = UURET_OK;

  return result;
}
예제 #3
0
int
UUInsertPartToList (uufile *data)
{
  uulist *iter = UUGlobalFileList, *unew;
  uufile *fiter, *last;

  /*
   * Part belongs together, if
   * (a) The file name received from the subject lines match _or_
   *     the MIME-IDs match,
   * (b) Not both parts have a begin line
   * (c) Not both parts have an end line
   * (d) Both parts don't have different MIME-IDs
   * (e) Both parts don't encode different files
   * (f) The other part wants to stay alone (FL_SINGLE)
   */

  /*
   * check if this part wants to be left alone. If so, don't bother
   * to do all the checks
   */

  while (iter) {
    if (data->data->flags & FL_SINGLE) {
      /* this space intentionally left blank */
    }
    else if ((_FP_stricmp (data->subfname, iter->subfname) == 0 ||
         (data->mimeid && iter->mimeid &&
          strcmp (data->mimeid, iter->mimeid) == 0)) &&
	!(iter->begin && data->data->begin) &&
	!(iter->end   && data->data->end) &&
	!(data->mimeid && iter->mimeid &&
	  strcmp (data->mimeid, iter->mimeid) != 0) &&
	!(data->filename && iter->filename &&
	  strcmp (data->filename, iter->filename) != 0) &&
	!(iter->flags & FL_SINGLE)) {

      /*
       * if we already have this part, don't try to insert it
       */

      for (fiter=iter->thisfile;
	   fiter && (data->partno>fiter->partno) && !fiter->data->end;
	   fiter=fiter->NEXT)
	/* empty loop */ ;
      if (fiter && 
	  (data->partno==fiter->partno || 
	   (data->partno > fiter->partno && fiter->data->end)))
	goto goahead;

      if (iter->filename == NULL && data->filename != NULL) {
        if ((iter->filename = _FP_strdup (data->filename)) == NULL)
	  return UURET_NOMEM;
      }

      /*
       * special case when we might have tagged a part as Base64 when the
       * file was really XX
       */

      if (data->data->uudet == B64ENCODED && 
	  iter->uudet == XX_ENCODED && iter->begin) {
	data->data->uudet = XX_ENCODED;
      }
      else if (data->data->uudet == XX_ENCODED && data->data->begin &&
	       iter->uudet == B64ENCODED) {
	iter->uudet = XX_ENCODED;

	fiter = iter->thisfile;
	while (fiter) {
	  fiter->data->uudet = XX_ENCODED;
	  fiter = fiter->NEXT;
	}
      }

      /*
       * If this is from a Message/Partial, we believe only the
       * iter->uudet from the first part
       */
      if (data->data->flags & FL_PARTIAL) {
	if (data->partno == 1) {
	  iter->uudet = data->data->uudet;
	  iter->flags = data->data->flags;
	}
      }
      else {
	if (data->data->uudet) iter->uudet = data->data->uudet;
	if (data->data->flags) iter->flags = data->data->flags;
      }

      if (iter->mode == 0 && data->data->mode != 0)
        iter->mode = data->data->mode;
      if (data->data->begin) iter->begin = (data->partno)?data->partno:1;
      if (data->data->end)   iter->end   = (data->partno)?data->partno:1;

      if (data->mimetype) {
	_FP_free (iter->mimetype);
	iter->mimetype = _FP_strdup (data->mimetype);
      }

      /*
       * insert part at the beginning
       */

      if (data->partno != -1 && data->partno < iter->thisfile->partno) {
	iter->state    = UUFILE_READ;
	data->NEXT     = iter->thisfile;
	iter->thisfile = data;
	return UURET_OK;
      }

      /*
       * insert part somewhere else
       */

      iter->state = UUFILE_READ;	/* prepare for re-checking */
      fiter       = iter->thisfile;
      last        = NULL;

      while (fiter) {
	/*
	 * if we find the same part no again, check which one looks better
	 */
	if (data->partno == fiter->partno) {
          if (fiter->data->subject == NULL)
            return UURET_NODATA;
	  else if (_FP_stristr (fiter->data->subject, "repost") != NULL &&
		   _FP_stristr (data->data->subject,  "repost") == NULL)
	    return UURET_NODATA;
          else if (fiter->data->uudet && !data->data->uudet)
            return UURET_NODATA;
          else {
	    /*
	     * replace
	     */
            data->NEXT  = fiter->NEXT;
            fiter->NEXT = NULL;
            UUkillfile (fiter);

            if (last == NULL)
              iter->thisfile = data;
            else
              last->NEXT     = data;

            return UURET_OK;
          }
        }

	/*
	 * if at the end of the part list, add it
	 */

	if (fiter->NEXT == NULL || 
	    (data->partno != -1 && data->partno < fiter->NEXT->partno)) {
	  data->NEXT  = fiter->NEXT;
	  fiter->NEXT = data;

	  if (data->partno == -1)
	    data->partno = fiter->partno + 1;

	  return UURET_OK;
	}
        last  = fiter;
	fiter = fiter->NEXT;
      }
      
      return UURET_OK; /* Shouldn't get here */
    }
  goahead:
    /*
     * we need iter below
     */
    if (iter->NEXT == NULL) 
      break;

    iter = iter->NEXT;
  }
  /*
   * handle new entry
   */

  if (data->partno == -1) {
    /*
     * if it's got no part no, and it's MIME mail, then assume this is
     * part no. 1. If it's not MIME, then we can't handle it; if it
     * had a 'begin', it'd have got a part number assigned by
     * UUPreProcessPart().
     */
    if (data->data->uudet == B64ENCODED || data->data->uudet == BH_ENCODED)
      data->partno = 1;
    else
      return UURET_NODATA;
  }

  if ((unew = (uulist *) malloc (sizeof (uulist))) == NULL) {
    return UURET_NOMEM;
  }

  if ((unew->subfname = _FP_strdup (data->subfname)) == NULL) {
    _FP_free (unew);
    return UURET_NOMEM;
  }

  if (data->filename != NULL) {
    if ((unew->filename = _FP_strdup (data->filename)) == NULL) {
      _FP_free (unew->subfname);
      _FP_free (unew);
      return UURET_NOMEM;
    }
  }
  else
    unew->filename = NULL;

  if (data->mimeid != NULL) {
    if ((unew->mimeid = _FP_strdup (data->mimeid)) == NULL) {
      _FP_free (unew->subfname);
      _FP_free (unew->filename);
      _FP_free (unew);
      return UURET_NOMEM;
    }
  }
  else
    unew->mimeid = NULL;

  if (data->mimetype != NULL) {
    if ((unew->mimetype = _FP_strdup (data->mimetype)) == NULL) {
      _FP_free (unew->mimeid);
      _FP_free (unew->subfname);
      _FP_free (unew->filename);
      _FP_free (unew);
      return UURET_NOMEM;
    }
  }
  else
    unew->mimetype = NULL;

  unew->state     = UUFILE_READ;
  unew->binfile   = NULL;
  unew->thisfile  = data;
  unew->mode      = data->data->mode;
  unew->uudet     = data->data->uudet;
  unew->flags     = data->data->flags;
  unew->begin     = (data->data->begin) ? ((data->partno)?data->partno:1) : 0;
  unew->end       = (data->data->end)   ? ((data->partno)?data->partno:1) : 0;
  unew->misparts  = NULL;
  unew->haveparts = NULL;
  unew->NEXT      = NULL;

  if (iter == NULL)
    UUGlobalFileList = unew;
  else
    iter->NEXT = unew;

  return UURET_OK;
}
예제 #4
0
uulist *
UUCheckGlobalList (void)
{
  int misparts[MAXPLIST], haveparts[MAXPLIST];
  int miscount, havecount, count, flag, part;
  uulist *liter=UUGlobalFileList, *prev;
  uufile *fiter;
  long thesize;

  while (liter) {
    miscount = 0;
    thesize  = 0;

    if (liter->state & UUFILE_OK) {
      liter = liter->NEXT;
      continue;
    }
    else if ((liter->uudet == QP_ENCODED ||
	      liter->uudet == PT_ENCODED) && 
	     (liter->flags & FL_SINGLE)) {
      if ((liter->flags&FL_PROPER)==0)
	liter->size = -1;
      else
	liter->size = liter->thisfile->data->length;

      liter->state = UUFILE_OK;
      continue;
    }
    else if ((fiter = liter->thisfile) == NULL) {
      liter->state = UUFILE_NODATA;
      liter = liter->NEXT;
      continue;
    }

    /*
     * Re-Check this file
     */

    flag      = 0;
    miscount  = 0;
    havecount = 0;
    thesize   = 0;
    liter->state = UUFILE_READ;

    /*
     * search encoded data
     */

    while (fiter && !fiter->data->uudet) {
      if (havecount<MAXPLIST) {
	haveparts[havecount++] = fiter->partno;
      }
      fiter = fiter->NEXT;
    }

    if (fiter == NULL) {
      liter->state = UUFILE_NODATA;
      liter = liter->NEXT;
      continue;
    }

    if (havecount<MAXPLIST) {
      haveparts[havecount++] = fiter->partno;
    }

    if ((part = fiter->partno) > 1) {
      if (!fiter->data->begin) {
	for (count=1; count < part && miscount < MAXPLIST; count++)
	  misparts[miscount++] = count;
      }
    }

    /*
     * don't care if so many parts are missing
     */

    if (miscount >= MAXPLIST) {
      liter->state = UUFILE_MISPART;
      liter        = liter->NEXT;
      continue;
    }

    if (liter->uudet == B64ENCODED ||
	liter->uudet == QP_ENCODED ||
	liter->uudet == PT_ENCODED)
      flag |= 3; /* Don't need begin or end with Base64 or plain text*/

    if (fiter->data->begin) flag |= 1;
    if (fiter->data->end)   flag |= 2;
    if (fiter->data->uudet) flag |= 4; 

    /*
     * guess size of part
     */

    switch (fiter->data->uudet) {
    case UU_ENCODED:
    case XX_ENCODED:
      thesize += 3*fiter->data->length/4;
      thesize -= 3*fiter->data->length/124; /* substract 2 of 62 chars */
      break;
    case B64ENCODED:
      thesize += 3*fiter->data->length/4;
      thesize -=  fiter->data->length/52;   /* substract 2 of 78 chars */
      break;
    case QP_ENCODED:
    case PT_ENCODED:
      thesize += fiter->data->length;
      break;
    }
      
    fiter = fiter->NEXT;

    while (fiter != NULL) {
      for (count=part+1; count<fiter->partno && miscount<MAXPLIST; count++)
	misparts[miscount++] = count;

      part = fiter->partno;
      
      if (havecount<MAXPLIST)
	haveparts[havecount++]=part;

      if (fiter->data->begin) flag |= 1;
      if (fiter->data->end)   flag |= 2;
      if (fiter->data->uudet) flag |= 4;

      switch (fiter->data->uudet) {
      case UU_ENCODED:
      case XX_ENCODED:
	thesize += 3*fiter->data->length/4;
	thesize -= 3*fiter->data->length/124; /* substract 2 of 62 chars */
	break;
      case B64ENCODED:
	thesize += 3*fiter->data->length/4;
	thesize -=  fiter->data->length/52;   /* substract 2 of 78 chars */
	break;
      case QP_ENCODED:
      case PT_ENCODED:
	thesize += fiter->data->length;
	break;
      }

      if (fiter->data->end)
	break;
	
      fiter = fiter->NEXT;
    }

    /*
     * if in fast mode, we don't notice an 'end'. So if its uu or xx
     * encoded, there's a begin line and encoded data, assume it's
     * there.
     */
    
    if (uu_fast_scanning && (flag & 0x01) && (flag & 0x04) &&
	(liter->uudet == UU_ENCODED || liter->uudet == XX_ENCODED))
      flag |= 2;

    /*
     * Set the parts we have and/or missing
     */

    _FP_free (liter->haveparts);
    _FP_free (liter->misparts);

    liter->haveparts = NULL;
    liter->misparts  = NULL;
    
    if (havecount) {
      if ((liter->haveparts=(int*)malloc((havecount+1)*sizeof(int)))!=NULL) {
	memcpy (liter->haveparts, haveparts, havecount*sizeof(int));
	liter->haveparts[havecount] = 0;
      }
    }
    
    if (miscount) {
      if ((liter->misparts=(int*)malloc((miscount+1)*sizeof(int)))!=NULL) {
	memcpy (liter->misparts, misparts, miscount*sizeof(int));
	liter->misparts[miscount] = 0;
      }
      liter->state |= UUFILE_MISPART;
    }

    /*
     * Finalize checking
     */

    if ((flag & 4) == 0) liter->state |= UUFILE_NODATA;
    if ((flag & 1) == 0) liter->state |= UUFILE_NOBEGIN;
    if ((flag & 2) == 0) liter->state |= UUFILE_NOEND;
    
    if ((flag & 7) == 7 && miscount==0) {
      liter->state = UUFILE_OK;
    }

    if ((uu_fast_scanning && (liter->flags&FL_PROPER)==0) || thesize<=0)
      liter->size = -1;
    else
      liter->size = thesize;

    if (liter->state==UUFILE_OK && 
        (liter->filename==NULL || liter->filename[0]=='\0')) {
      /*
       * Emergency backup if the file does not have a filename
       */
      _FP_free (liter->filename);
      if (liter->subfname && liter->subfname[0] &&
          _FP_strpbrk (liter->subfname, "()[];: ") == NULL)
        liter->filename = _FP_strdup (liter->subfname);
      else {
        sprintf (uucheck_tempname, "%s.%03d", nofname, ++nofnum);
        liter->filename = _FP_strdup (uucheck_tempname);
      }
    }
    liter = liter->NEXT;
  }

  /*
   * Sets back (PREV) links
   */

  liter = UUGlobalFileList;
  prev  = NULL;

  while (liter) {
    liter->PREV = prev;
    prev        = liter;
    liter       = liter->NEXT;
  }

  return UUGlobalFileList;
}