解析FTP LIST命令返回的目录列表

本文涉及的产品
全局流量管理 GTM,标准版 1个月
云解析 DNS,旗舰版 1个月
公共DNS(含HTTPDNS解析),每月1000万次HTTP解析
简介:
有个程序要分析FTP服务器返回的目录列表,本来以为比较简单,也在网上查了几个帖子,可都是一知半解的。于是下载了Filezilla的源代码,她的源文件
directorylistingparser.h
directorylistingparser.cpp
就是解析目录列表的,有同样需求的不妨看一看,还是挺费事的,不同平台要都要特殊处理。我把头文件贴出来:


#ifndef __DIRECTORYLISTINGPARSER_H__
#define __DIRECTORYLISTINGPARSER_H__

/* This class is responsible for parsing the directory listings returned by
 * the server.
 * Unfortunatly, RFC959 did not specify the format of directory listings, so
 * each server uses its own format. In addition to that, in most cases the 
 * listings were not designed to be machine-parsable, they were meant to be
 * human readable by users of that particular server.
 * By far the most common format is the one returned by the Unix "ls -l"
 * command. However, legacy systems are still in place, especially in big
 * companies. These often use very exotic listing styles.
 * Another problem are localized listings containing date strings. In some
 * cases these listings are ambiguous and cannot be distinguished.
 * Example for an ambiguous date: 04-05-06. All of the 6 permutations for
 * the location of year, month and day are valid dates.
 * Some servers send multiline listings where a single entry can span two
 * lines, this has to be detected as well, as far as possible.
 *
 * Some servers send MVS style listings which can consist of just the 
 * filename without any additional data. In order to prevent problems, this 
 * format is only parsed if the server is in fact recognizes as MVS server.
 *
 * Please see tests/dirparsertest.cpp for a list of supported formats and the
 * expected parser result.
 *
 * If adding data to the parser, it first decomposes the raw data into lines,
 * which then are processed further. Each line gets consecutively tested for
 * different formats, starting with the most common Unix style format.
 * Lines not containing a recognized format (e.g. a part of a multiline
 * entry) are rememberd and if the next line cannot be parsed either, they
 * get concatenated to be parsed again (and discarded if not recognized).
 */


class CLine;
class CToken;
class CControlSocket;
class CDirectoryListingParser
{
public:
  CDirectoryListingParser(CControlSocket* pControlSocket,  const CServer& server);
  ~CDirectoryListingParser();

  CDirectoryListing Parse( const CServerPath &path);

   void AddData( char *pData,  int len);
   void AddLine( const wxChar* pLine);

   void Reset();

   void SetTimezoneOffset( const wxTimeSpan& span) { m_timezoneOffset = span; }

   void SetServer( const CServer& server) { m_server = server; };

protected:
  CLine *GetLine( bool breakAtEnd =  false);

   void ParseData( bool partial);

   bool ParseLine(CLine *pLine,  const  enum ServerType serverType,  bool concatenated);

   bool ParseAsUnix(CLine *pLine, CDirentry &entry,  bool expect_date);
   bool ParseAsDos(CLine *pLine, CDirentry &entry);
   bool ParseAsEplf(CLine *pLine, CDirentry &entry);
   bool ParseAsVms(CLine *pLine, CDirentry &entry);
   bool ParseAsIbm(CLine *pLine, CDirentry &entry);
   bool ParseOther(CLine *pLine, CDirentry &entry);
   bool ParseAsWfFtp(CLine *pLine, CDirentry &entry);
   bool ParseAsIBM_MVS(CLine *pLine, CDirentry &entry);
   bool ParseAsIBM_MVS_PDS(CLine *pLine, CDirentry &entry);
   bool ParseAsIBM_MVS_PDS2(CLine *pLine, CDirentry &entry);
   bool ParseAsIBM_MVS_Migrated(CLine *pLine, CDirentry &entry);
   bool ParseAsMlsd(CLine *pLine, CDirentry &entry);
   bool ParseAsOS9(CLine *pLine, CDirentry &entry);
  
   // Only call this if servertype set to ZVM since it conflicts
   // with other formats.
   bool ParseAsZVM(CLine *pLine, CDirentry &entry);

   // Only call this if servertype set to HPNONSTOP since it conflicts
   // with other formats.
   bool ParseAsHPNonstop(CLine *pLine, CDirentry &entry);

   // Date / time parsers
   bool ParseUnixDateTime(CLine *pLine,  int &index, CDirentry &entry);
   bool ParseShortDate(CToken &token, CDirentry &entry,  bool saneFieldOrder =  false);
   bool ParseTime(CToken &token, CDirentry &entry);

   // Parse file sizes given like this: 123.4M
   bool ParseComplexFileSize(CToken& token, wxLongLong& size,  int blocksize = -1);

   bool GetMonthFromName( const wxString& name,  int &month);

  CControlSocket* m_pControlSocket;

   static std::map<wxString,  int> m_MonthNamesMap;
  
   struct t_list
  {
     char *p;
     int len;
  };
   int m_currentOffset;

  std::list<t_list> m_DataList;
  std::list<CDirentry> m_entryList;

  CLine *m_prevLine;

  CServer m_server;

   bool m_fileListOnly;
  std::list<wxString> m_fileList;
  
   bool m_maybeMultilineVms;

  wxTimeSpan m_timezoneOffset;
};

#endif









本文转自 h2appy  51CTO博客,原文链接:http://blog.51cto.com/h2appy/122279,如需转载请自行联系原作者
目录
相关文章
|
1月前
|
人工智能 Java
Java 中数组Array和列表List的转换
本文介绍了数组与列表之间的相互转换方法,主要包括三部分:1)使用`Collections.addAll()`方法将数组转为列表,适用于引用类型,效率较高;2)通过`new ArrayList&lt;&gt;()`构造器结合`Arrays.asList()`实现类似功能;3)利用JDK8的`Stream`流式计算,支持基本数据类型数组的转换。此外,还详细讲解了列表转数组的方法,如借助`Stream`实现不同类型数组间的转换,并附带代码示例与执行结果,帮助读者深入理解两种数据结构的互转技巧。
Java 中数组Array和列表List的转换
|
25天前
|
容器
HarmonyOS NEXT - 列表布局(List)
列表(List)是一种用于展示结构化、可滚动信息的复杂容器,适用于同类数据集合的呈现(如通讯录、音乐列表等)。通过垂直或水平排列子组件`ListItem`或`ListItemGroup`,可实现单个视图或多视图组合。支持条件渲染、循环渲染和懒加载等优化方式。 - **分隔线**:通过`divider`属性添加分隔线,并自定义粗细、颜色及边距。 - **滚动条**:使用`scrollBar`属性控制滚动条显示,支持按需显示(`BarState.Auto`)。 - **代码示例**:包含静态列表项、分组头布局、循环渲染及分隔线配置。
79 0
|
1月前
|
索引
【Flutter 开发必备】AzListView 组件全解析,打造丝滑索引列表!
在 Flutter 开发中,AzListView 是实现字母索引分类列表的理想选择。它支持 A-Z 快速跳转、悬浮分组标题、自定义 UI 和高效性能,适用于通讯录、城市选择等场景。本文将详细解析 AzListView 的核心参数和实战示例,助你轻松实现流畅的索引列表。
67 7
|
3月前
|
运维 Shell 数据库
Python执行Shell命令并获取结果:深入解析与实战
通过以上内容,开发者可以在实际项目中灵活应用Python执行Shell命令,实现各种自动化任务,提高开发和运维效率。
122 20
|
3月前
|
网络协议 Unix Linux
深入解析:Linux网络配置工具ifconfig与ip命令的全面对比
虽然 `ifconfig`作为一个经典的网络配置工具,简单易用,但其功能已经不能满足现代网络配置的需求。相比之下,`ip`命令不仅功能全面,而且提供了一致且简洁的语法,适用于各种网络配置场景。因此,在实际使用中,推荐逐步过渡到 `ip`命令,以更好地适应现代网络管理需求。
107 11
|
4月前
|
存储 SpringCloudAlibaba Java
【SpringCloud Alibaba系列】一文全面解析Zookeeper安装、常用命令、JavaAPI操作、Watch事件监听、分布式锁、集群搭建、核心理论
一文全面解析Zookeeper安装、常用命令、JavaAPI操作、Watch事件监听、分布式锁、集群搭建、核心理论。
【SpringCloud Alibaba系列】一文全面解析Zookeeper安装、常用命令、JavaAPI操作、Watch事件监听、分布式锁、集群搭建、核心理论
|
4月前
|
C语言 Python
[oeasy]python054_python有哪些关键字_keyword_list_列表_reserved_words
本文介绍了Python的关键字列表及其使用规则。通过回顾`hello world`示例,解释了Python中的标识符命名规则,并探讨了关键字如`if`、`for`、`in`等不能作为变量名的原因。最后,通过`import keyword`和`print(keyword.kwlist)`展示了Python的所有关键字,并总结了关键字不能用作标识符的规则。
85 9
|
4月前
|
数据挖掘 大数据 数据处理
python--列表list切分(超详细)
通过这些思维导图和分析说明表,您可以更直观地理解Python列表切分的概念、用法和实际应用。希望本文能帮助您更高效地使用Python进行数据处理和分析。
116 14
|
4月前
|
安全 编译器 Linux
深入解析与防范:基于缓冲区溢出的FTP服务器攻击及调用计算器示例
本文深入解析了利用缓冲区溢出漏洞对FTP服务器进行远程攻击的技术,通过分析FreeFlow FTP 1.75版本的漏洞,展示了如何通过构造过长的用户名触发缓冲区溢出并调用计算器(`calc.exe`)。文章详细介绍了攻击原理、关键代码组件及其实现步骤,并提出了有效的防范措施,如输入验证、编译器保护和安全编程语言的选择,以保障系统的安全性。环境搭建基于Windows XP SP3和Kali Linux,使用Metasploit Framework进行攻击演示。请注意,此内容仅用于教育和研究目的。
135 4
|
4月前
|
数据挖掘 大数据 数据处理
python--列表list切分(超详细)
通过这些思维导图和分析说明表,您可以更直观地理解Python列表切分的概念、用法和实际应用。希望本文能帮助您更高效地使用Python进行数据处理和分析。
246 10

热门文章

最新文章

推荐镜像

更多
下一篇
oss创建bucket