我现在正在研究几个程序,并且对我调试程序和日志错误的一些杂乱无章的方式感到沮丧。因此,我决定花几天时间编写一个错误库,我可以在我的所有程序中使用这个库。我在Windows中进行了大部分的开发,广泛使用了Windows API,但这里的关键是灵活性:这个库在理想情况下需要保持灵活性,在Windows和类Unix环境中提供控制台应用程序和GUI应用程序中的程序员通知选项。
我最初的想法是使用一个库,它使用基于当前环境的windows和unix头的预处理条件包含。例如,在win32应用程序中,控制台错误消息通知(尽管可能)是不必要的;相反,一个简单的
MessageBoxA/W(hWndParent, TEXT("Some error message that makes sense in context"), TEXT("Application Name"), MB_ICONERROR | MB_OK)最合情合理。另一方面,在linux上,事情要复杂一些:
GtkWindow *w;
w = gtk_message_dialog_new(pOwner, GTK_DIALOG_MODAL, GTK_MESSAGE_ERROR, GTK_BUTTONS_OK, TEXT("Some error message");
gtk_window_set_title(w, TEXT("Application Name"));在这两种操作中,简单的文件日志记录包含有关错误(函数、文件、行等)的更多信息。在精确定位源和跟踪流方面也很有用。
此外,日志记录应该是可能的:即使调用了需要错误日志记录/通知的函数,如果激活了该级别的日志记录,也应该可以在程序中显示函数调用的顺序。
因此,我最初的考虑是拥有一个包含所有这些特性的库,通过预处理器条件来最小化开销。我认为把它分解成几个结构是最有意义的:
“”结构,它被传递给需要日志记录的主程序中的每个函数,并包含
)。
这只是我对这个图书馆的初步想法。你们中有谁能想到更多我应该包括的信息吗?对我来说,另一个主要问题是错误添加的原子性:可能是另一个线程创建错误,而不是记录错误,因此我需要确保创建和添加错误节点实际上是一个原子操作。因此,互斥很可能是我进行同步的方式。
谢谢你的帮助!
发布于 2011-06-03 09:55:03
在非CRITICALERROR的情况下,应用程序将在日志调用后继续运行,最好将每个日志结构(线程安全生产者-消费者队列)排队到执行请求的操作/s的日志线程。日志线程通常在处理它们之后释放结构。一些优点:
1)将每个日志记录请求的操作简化为对结构进行错误定位、加载结构并将其推送到队列中。如果磁盘暂时处于繁忙状态,或者由于磁盘位于网络上而具有较高的延迟时间,或者实际上不可用,则调用线程/s将几乎继续正常运行。这样,仅仅因为日志打开就会失败的一组应用程序就会减少。有一些无法重现的间歇性问题的用户可以被指示打开记录器,而日志记录几乎不可能影响正常操作,或者更糟糕的是,引入隐藏错误的延迟。
( 2)出于与(1)相同的原因,即使在运行时,添加/更改记录器功能也要容易得多。例如,您希望限制日志文件的大小或每天引发一个新的日期/时间戳日志文件。当旧文件关闭和新文件打开时,“正常”调用会给调用线程带来很长的延迟。如果日志记录被排队关闭,则只能暂时增加排队日志结构的数量。
3)控制测井更容易。在GUI应用程序中,记录器可以有自己的表单,可以修改日志记录选项。您可以有一个‘’按钮,当单击该按钮时,将一个'LOGCONTROL‘结构排队到日志线程,以及所有其他日志记录消息。当线程得到它时,它会打开一个新的日志文件。
4)转发日志消息相当容易。也许您希望查看记录的消息,并将它们写到磁盘队列上,形成一个“LOGCONTROL”结构,该结构指示线程保存传递到结构中的函数ptr,然后在将它们写入磁盘后使用后续的日志消息调用该函数。传递的函数可以将消息排队到GUI中,以便在“终端”类型窗口中显示( Windows上的PostMessage、Qt等具有类似的功能,可以将数据传递给GUI)。当然,在*x上,您可以打开一个控制台窗口,并打开日志文件“tail-f”,但是对于GUI用户来说,这看起来并不特别优雅,对于用户来说管理起来更困难,而且在Windows上也是不可用的,(有多少用户知道如何从控制台窗口复制粘贴并发送错误消息?)
另一种可能是,日志记录线程可能被指示将日志文本流到远程服务器--另一个'LOGCONTROL‘结构可以将主机名/端口传递给记录器线程。由于排队的通信,打开到服务器的网络连接的临时延迟并不重要。
5)“懒散写作”和其他此类性能增强变得更容易,但:
缺点:
1)主要是当日志调用返回给请求者时,日志操作可能还没有发生。在CRITICALERROR崩溃的情况下,这是非常坏的消息,在某些情况下,即使是对进度消息的“普通”日志记录,这也是不可接受的。在这些情况下,应该有一个绕过磁盘写入/刷新的选项-- fOpen/CreateFile,一个单独的'Direct.log',追加,写,刷新,关闭。缓慢但安全,以防应用程序在日志调用返回后爆炸。
2)更复杂,更多的开发,更多的条件,更大的API接口。
雷格斯·马丁
发布于 2011-06-04 08:59:11
嗨,我用这个作为另一种语言,但是你可以研究它并遵循它的设计http://www.gurock.com/smartinspect/。
问候
https://stackoverflow.com/questions/6222042
复制相似问题