CentOS为普通用户增加sudo权限
系统下面为普通用户增加sudo权限,方法为:
修改/etc/sudoers文件,修改命令必须为visudo才行
#visudo -f /etc/sudoers
像root ALL=(ALL) ALL 这样增加你所需要的用户
xxx ALL=(ALL) ALL
然后用xxx用户登录,测试时会发现
#sudo ifconfig
sudo: ifconfig: command not found
修改普通用户的.bash_profile文件在PATH变量中增加
增加:
/sbin:/usr/sbin:/usr/local/sbin:/usr/kerberos/sbin
然后重启机器,即可。
[转]Ultraedit使用:配置字数统计工具栏
有朋友在使用Ultraedit的时候,可能不知道Ultraedit可以对文档的字符数进行统计的,还把文字全都拷贝到word里,利用word的字数统计功能进行统计,那这样就失去了使用Ultraedit的意义了,其实用Ultraedit进行字数统计是非常容易的,只要点击一下工具栏中字数统计的按钮即可,但不幸的是,Ultraedit默认好像并不显示字数统计按钮,所以这个又得由我们自己配置,下面就说说如何让字数统计按钮显示在上部工具栏里。
1、 菜单选择:高级->配置,如下图所示:
2、配置:
在左侧列表中,点“定制”,然后在右侧点“定制工具栏”,弹出如下窗口
在右侧的“新建工具栏”里输入“自定义”(文字可随意),表示我们将建立一个自定义工具栏集,然后点文本框右边的图标,在左侧将新建一个工具栏集“自定义”。
然后在左侧选中刚才新建的工具栏集“自定义”,在右侧列表中找到“字数统计”,找到后,选中,按下图所说的处理。
3、 显示
示例如下:
php高并发状态下文件的读写
对于日IP不高或者说并发数不是很大的应用,一般不用考虑这些!!用一般的文件操作方法完全没有问题。但如果并发高,在我们对文件进行读写操作时,很有可能多个进程对进一文件进行操作,如果这时不对文件的访问进行相应的独占,就容易造成数据丢失。
例如:一个在线聊天室(这里假定把聊天内容写入文件),在同一时刻,用户A和用户B都要操作数据保存文件,首先是A打开了文件,然后更新里面的数据,但这里B也正好也打开了同一个文件,也准备更新里面的数据。当A把写好的文件保存时,这里其实B已经打开了文件。但当B再把文件保存回去时,这里已经造成了数据的丢失,因为这里B用户完全不知道它所打开的文件在它对其进行更改时,A用户也更改了这个文件,所以最后B用户保存更改时,用户A的更新就被会丢失。
对于这样的问题,一般的解决方案时当一进程对文件进行操作时,首先对其它进行加锁,意味着这里只有该进程有权对文件进行读取,其它进程如果现在读,是完全没有问题,但如果这时有进程试图想对其进行更新,会遭到操作拒绝,先前对文件进行加锁的进程这时如果对文件的更新操作完毕,这就释放独占的标识,这时文件又恢复到了可更改的状态。接下来同理,如果那个进程在操作文件时,文件没有加锁,这时,它就可以放心大胆的对文件进行锁定,独自享用。
所以一般的方案会是:
Php代码
[cc lang='php' ]
$fp = fopen ( "/tmp/lock.txt", "w+" );
if (flock ( $fp, LOCK_EX )) {
fwrite ( $fp, "Write something here\n" );
flock ( $fp, LOCK_UN );
} else {
echo "Couldn't lock the file !";
}
fclose ( $fp );
[/cc]
但在PHP中,flock似乎工作的不是那么好!在多并发情况下,似乎是经常独占资源,不即时释放,或者是根本不释放,造成死锁,从而使服务器的cpu占用很高,甚至有时候会让服务器彻底死掉。好像在很多linux/unix系统中,都会有这样的情况发生。
所以使用flock之前,一定要慎重考虑。
那么就没有解决方案了吗?其实也不是这样的。如果flock()我们使用得当,完全可能解决死锁的问题。当然如果不考虑使用flock()函数,也同样会有很好的解决方案来解决我们的问题。
经过我个人的搜集和总结,大致归纳了解决方案有如下几种。
方案一:对文件进行加锁时,设置一个超时时间.
大致实现如下:
Php代码
[cc lang='php' ]
if ($fp = fopen ( $fileName, 'a' )) {
$startTime = microtime ();
do {
$canWrite = flock ( $fp, LOCK_EX );
if (! $canWrite)
usleep ( round ( rand ( 0, 100 ) * 1000 ) );
} while ( (! $canWrite) && ((microtime () - $startTime) < 1000) );
if ($canWrite) {
fwrite ( $fp, $dataToSave );
}
fclose ( $fp );
}
[/cc]
超时设置为1ms,如果这里时间内没有获得锁,就反复获得,直接获得到对文件操作权为止,当然。如果超时限制已到,就必需马上退出,让出锁让其它进程来进行操作。
方案二:不使用flock函数,借用临时文件来解决读写冲突的问题。
大致原理如下:
1。将需要更新的文件考虑一份到我们的临时文件目录,将文件最后修改时间保存到一个变量,并为这个临时文件取一个随机的,不容易重复的文件名。
2。当对这个临时文件进行更新后,再检测原文件的最后更新时间和先前所保存的时间是否一致。
3。如果最后一次修改时间一致,就将所修改的临时文件重命名到原文件,为了确保文件状态同步更新,所以需要清除一下文件状态。
4。但是,如果最后一次修改时间和先前所保存的一致,这说明在这期间,原文件已经被修改过,这时,需要把临时文件删除,然后返回false,说明文件这时有其它进程在进行操作。
大致实现代码如下:
Php代码
[cc lang='php' ]
<?php
$dir_fileopen = "tmp";
function randomid() {
return time () . substr ( md5 ( microtime () ), 0, rand ( 5, 12 ) );
}
function cfopen($filename, $mode) {
global $dir_fileopen;
clearstatcache ();
do {
$id = md5 ( randomid ( rand (), TRUE ) );
$tempfilename = $dir_fileopen . "/" . $id . md5 ( $filename );
} while ( file_exists ( $tempfilename ) );
if (file_exists ( $filename )) {
$newfile = false;
copy ( $filename, $tempfilename );
} else {
$newfile = true;
}
$fp = fopen ( $tempfilename, $mode );
return $fp ? array ($fp, $filename, $id, @filemtime ( $filename ) ) : false;
}
function cfwrite($fp, $string) {
return fwrite ( $fp [0], $string );
}
function cfclose($fp, $debug = "off") {
global $dir_fileopen;
$success = fclose ( $fp [0] );
clearstatcache ();
$tempfilename = $dir_fileopen . "/" . $fp [2] . md5 ( $fp [1] );
if ((@filemtime ( $fp [1] ) == $fp [3]) || ($fp [4] == true && ! file_exists ( $fp [1] )) || $fp [5] == true) {
rename ( $tempfilename, $fp [1] );
} else {
unlink ( $tempfilename );
//说明有其它进程 在操作目标文件,当前进程被拒绝
$success = false;
}
return $success;
}
$fp = cfopen ( 'lock.txt', 'a+' );
cfwrite ( $fp, "welcome to beijing.\n" );
fclose ( $fp, 'on' );
[/cc]
对于上面的代码所使用的函数,需要说明一下:
1.rename();重命名一个文件或一个目录,该函数其实更像linux里的mv。更新文件或者目录的路径或名字很方便。
但当我在window测试上面代码时,如果新文件名已经存在,会给出一个notice,说当前文件已经存在。但在linux下工作的很好。
2.clearstatcache();清除文件的状态.php将缓存所有文件属性信息,以提供更高的性能,但有时,多进程在对文件进行删除或者更新操作时,php没来得及更新缓存里的文件属性,容易导致访问到最后更新时间不是真实的数据。所以这里需要使用该函数对已保存的缓存进行清除。
方案三:对操作的文件进行随机读写,以降低并发的可能性。
在对用户访问日志进行记录时,这种方案似乎被采用的比较多。
先前需要定义一个随机空间,空间越大,并发的的可能性就越小,这里假设随机读写空间为[1-500],那么我们的日志文件的分布就为log1~到log500不等。每一次用户访问,都将数据随机写到log1~log500之间的任一文件。
在同一时刻,有2个进程进行记录日志,A进程可能是更新的log32文件,而B进程呢?则此时更新的可能就为log399.要知道,如果要让B进程也操作log32,概率基本上为1/500,差不多约等于零。
在需要对访问日志进行分析时,这里我们只需要先将这些日志合并,再进行分析即可。
使用这种方案来记录日志的一个好处时,进程操作排队的可能性比较小,可以使进程很迅速的完成每一次操作。
方案四:将所有要操作的进程放入一个队列中。然后专门放一个服务完成文件操作。
队列中的每一个排除的进程相当于第一个具体的操作,所以第一次我们的服务只需要从队列中取得相当于具体操作事项就可以了,如果这里还有大量的文件操作进程,没关系,排到我们的队列后面即可,只要愿意排,队列的多长都没关系。
对于以前几种方案,各有各的好处!大致可能归纳为两类:
1。需要排队(影响慢)比如方案一、二、四
2。不需要排队。(影响快)方案三
在设计缓存系统时,一般我们不会采用方案三。因为方案三的分析程序和写入程序是不同步的,在写的时间,完全不考虑到时候分析的难度,只管写的行了。试想一下,如我们在更新一个缓存时,如果也采用随机文件读写法,那么在读缓存时似乎会增加很多流程。但采取方案一、二就完全不一样,虽然写的时间需要等待(当获取锁不成功时,会反复获取),但读文件是很方便的。添加缓存的目的就是要减少数据读取瓶颈,从而提高系统性能。
从上为个人经验和一些资料的总结,有什么不对的地方,或者没有谈到的地方,欢迎各位同学指正。
[原创]破解xmind3.2专业版功能
花了一天时间,其实是一个晚上的时间,突然觉得很好用,但是默认版本只有导出png功能,本来考虑买个正版的,一看价格,我崩溃了,好像买不起……
又想用,又买不起,怎么办?google了下,没有任何破解,只有3.1.1版本有个同学做了一个破解,download下来看了下,他的原理是绕过验证请求,用zip解压了plugins/net.xmind.verify_3.2.0.201009142023.jar文件,将net\xmind\verify\internal\UserInfoVerifier.class文件进行了还原,发现作者用了内部类,那个美元“$”相当纠结了,至少我就被他卡死了,用了很多方法编译都没有成功,提示的都是内部类引起的无法找到符号的问题,算了作罢吧,这条路太纠结了,怎么办?
这条路不行,那我就换嘛,
破解需要的准备工作:将plugins的所有文件解压在本地,也就是将classpath目录移到一个目录(本人解压在了plugins3),方便javac和查找,嘿嘿
用UE搜索“pdf”,嘿嘿,找到了导出代码的位置:\org\xmind\ui\internal\exports的PDFExportWizard.class,也就是org.xmind.ui.exports_3.2.0.201009142023.jar文件,用jd-gui-0.3.3.windows软件直接打开解压的目录,就可以很方便的看源码了,据说有问题,但是大致看看还是可以的:
打开后看到:
protected void addValidPages() {
addPage(new VerifyPage(ExportMessages.PDFExportJob_Name));
addPage(this.page = new PDFExportPage());
}
原来是增加了:addPage(new VerifyPage(ExportMessages.PDFExportJob_Name));
那么继续找VerifyPage类:
public VerifyPage(String name)
{
super("org.xmind.ui.export.verify", ExportMessages.VerifyPage_Title, null);
setPageComplete(false);
this.name = name;
}
public void setVisible(boolean visible)
{
super.setVisible(visible);
if (visible)
VerifyUI.runAction(this.name, new IVerifyListener() {
public void notifyValidity(IStatus validity) {
if (validity.getCode() == 1) {
VerifyPage.this.setPageComplete(true);
IWizardPage next = VerifyPage.this.getNextPage();
if (next != null) {
IWizardPage previous = VerifyPage.this.getPreviousPage();
VerifyPage.this.getContainer().showPage(next);
next.setPreviousPage(previous);
}
}
}
});
}
好,看到这里会看代码的就知道接下来改干什么了,不知道?呃,面壁去……
好啦,好晚了,也困了,就直接讲下吧:
将第二个函数直接引导至下一页即可:
public void setVisible(boolean visible)
{
super.setVisible(visible);
VerifyPage.this.setPageComplete(true);
IWizardPage next = VerifyPage.this.getNextPage();
VerifyPage.this.getContainer().showPage(next);
}
javac编译:
C:\Users\Administrator>C:\PROGRA~1\Java\JDK16~1.0_2\bin\javac.exe -classpath E:\
tt\XMind\plugins3\ -d E:\tt\XMind\plugins\org.xmind.ui.exports_3.2.0.20100914202
3 E:\tt\XMind\plugins3\org\xmind\ui\internal\exports\VerifyPage.java
成class文件,替换掉原来的,然后用zip打包,改后缀为.jar,替换原来的文件,打开xmind程序,测试导出功能,OK
由于涉及到版权问题,这里就不将破解文件公布了,需要的可以自行破解,或者留下email,呵呵,我会尽快邮件给你测试,请将破解文件在24小时内删除,否则牵扯到版权纠纷,一律与本站与本人无关。
----------------------------2010.10.16 00:30分割线----------------------------------------
昨天这个时候完成了export的破解,还有录音,头脑风暴等功能不能使用,嘿嘿,今天耐着性子看完了UserInfoVerifier.class的代码,结合jd-gui-0.3.3.windows和DJ Java Decompiler 3.11各自还原的java代码进行中和,顺利的完成了javac的再编译,嘿嘿,自此,在源头上破解了pro版本。经测试,用普通账户登录即可使用pro功能,需要测试的同学可以邮我。
具体破解方法如上,打包替换,以下是我校验的java代码。
只供有需要的朋友体验正式版功能,如果觉得不错,强烈建议购买正版!
[转]小议TCP的MSS(最大分段)以及MTU
[前言]
漫漫51长假,没有好的去处,只能每日上网消遣,某日逛到NBO灌水,见一帖曰:无法通过2514路由器上MSN(出口为ADSL线路,通过PPPoE)吾心想,ADSL---PPPoE,那肯定就是MTU之问题。回帖告之:改PC之MTU。
过数日,又逛到NBO,又见这帖,后有人回曰:ip tcp adjust-mss 1452后帖主又跟:问题解决。
吾纳闷之,后百思而得其解,So决定将自己所得写出来,分享给大家。
[背景知识]
MTU: Maxitum Transmission Unit 最大传输单元
MSS: Maxitum Segment Size 最大分段大小(偶是直译,翻译的不好,不要打
俺PP)
PPPoE: PPP Over Ethernet(在以太网上承载PPP协议)
[分析过程]
先说说这MTU最大传输单元,这个最大传输单元实际上和链路层协议有着密切的关系,让我们先仔细回忆一下EthernetII帧的结构DMAC+SMAC+Type+Data+CRC
由于以太网传输电气方面的限制,每个以太网帧都有最小的大小64bytes最大不能超过1518bytes,对于小于或者大于这个限制的以太网帧我们都可以视之为错误的数据帧,一般的以太网转发设备会丢弃这些数据帧。
(注:小于64Bytes的数据帧一般是由于以太网冲突产生的“碎片”或者线路干扰或者坏的以太网接口产生的,对于大于1518Bytes的数据帧我们一般把它叫做Giant帧,这种一般是由于线路干扰或者坏的以太网口产生)
由于以太网EthernetII最大的数据帧是1518Bytes这样,刨去以太网帧的帧头(DMAC目的MAC地址48bit=6Bytes+SMAC源MAC地址48bit=6Bytes+Type域2bytes)14Bytes和帧尾CRC校验部分4Bytes(这个部门有时候大家也把它叫做FCS),那么剩下承载上层协议的地方也就是Data域最大就只能有1500Bytes这个值我们就把它称之为MTU。这个就是网络层协议非常关心的地方,因为网络层协议比如IP协议会根据这个值来决定是否把上层传下来的数据进行分片。就好比一个盒子没法装下一大块面包,我们需要把面包切成片,装在多个盒子里面一样的道理。
当两台远程PC互联的时候,它们的数据需要穿过很多的路由器和各种各样的网络媒介才能到达对端,网络中不同媒介的MTU各不相同,就好比一长段的水管,由不同粗细的水管组成(MTU不同 )通过这段水管最大水量就要由中间最细的水管决定。
对于网络层的上层协议而言(我们以TCP/IP协议族为例)它们对水管粗细不在意它们认为这个是网络层的事情。网络层IP协议会检查每个从上层协议下来的数据包的大小,并根据本机MTU的大小决定是否作“分片”处理。分片最大的坏处就是
降低了传输性能,本来一次可以搞定的事情,分成多次搞定,所以在网络层更高一层(就是传输层)的实现中往往会对此加以注意!有些高层因为某些原因就会要求我这个面包不能切片,我要完整地面包,所以会在IP数据包包头里面加上一
个标签:DF(Donot Fragment)。这样当这个IP数据包在一大段网络(水管里面)传输的时候,如果遇到MTU小于IP数据包的情况,转发设备就会根据要求丢弃这个数据包。然后返回一个错误信息给发送者。这样往往会造成某些通讯上的问题,不过幸运的是大部分网络链路都是MTU1500或者大于1500。
对于UDP协议而言,这个协议本身是无连接的协议,对数据包的到达顺序以及是否正确到达不甚关心,所以一般UDP应用对分片没有特殊要求。
对于TCP协议而言就不一样了,这个协议是面向连接的协议,对于TCP协议而言它非常在意数据包的到达顺序以及是否传输中有错误发生。所以有些TCP应用对分片有要求---不能分片(DF)。
花开两朵,各表一枝,说完MTU的故事我们该讲讲今天的第二个猪脚---PPPoE所谓PPPoE就是在以太网上面跑PPP协议,有人奇怪了,PPP协议和Ethernet不都是链路层协议吗?怎么一个链路层跑到另外一个链路层上面去了,难道升级成网络层协议了不成。其实这是个误区:就是某层协议只能承载更上一层协议。
为什么会产生这种奇怪的需求呢?这是因为随着宽带接入(这种宽带接入一般为Cable Modem或者xDSL或者以太网的接入)由于以太网缺乏认证计费机制而传统运营商是通过PPP协议来对拨号等接入服务进行认证计费的,所以就出了这么一个怪胎:PPPoE。(有关PPPoE的详细介绍参见V大以及本站其他成员的一些介绍文章,我就不啰里啰唆的了)
PPPoE带来了好处,也带来了一些坏处,比如:二次封装耗费资源,降低了传输效能等等,这些坏处俺也不多说了,最大的坏处就是PPPoE导致MTU变小了以太网的MTU是1500,再减去PPP的包头包尾的开销(8Bytes),就变成1492。
如果两台主机之间的某段网络使用了PPPoE那么就会导致某些不能分片的应用无法通讯。
这个时候就需要我们调整一下主机的MTU,通过降低主机的MTU,这样我们就能够顺利地进行通讯了。
当然对于TCP应用而言还有另外的解决方案。
马上请出今天第三位猪脚:MSS。
MSS最大传输大小的缩写,是TCP协议里面的一个概念。
MSS就是TCP数据包每次能够传输的最大数据分段。为了达到最佳的传输效能TCP协议在建立连接的时候通常要协商双方的MSS值,这个值TCP协议在实现的时候往往用MTU值代替(需要减去IP数据包包头的大小20Bytes和TCP数据段的包头20Bytes)所以往往MSS为1460。通讯双方会根据双方提供的MSS值得最小值确定为这次连接的最大MSS值。
介绍完这三位猪脚s
我们回过头来看前言里面的那个问题,我们试想一下,如果我们在中间路由器上把每次TCP连接的最大MSS进行调整这样使得通过PPPoE链路的最大MSS值加上数据包头包尾不会超过PPPoE的MTU大小1492这样就不会造成无法通讯的问题.所以上面的问题可以通过ip tcp adjust-mss 1452来解决。
当然问题也可以通过修改PC机的MTU来解决。
[后记]
Cisco的TCP Adjust MSS Feature:
The TCP MSS Adjustment feature enables the configuration of the
maximum segment size (MSS) for transient packets that traverse a router,
specifically TCP segments in the SYN bit set, when Point to Point Protocol
over Ethernet (PPPoE) is being used in the network. PPPoE truncates the
Ethernet maximum transmission unit (MTU) 1492, and if the effective MTU
on the hosts (PCs) is not changed, the router in between the host and the
server can terminate the TCP sessions. The ip tcp adjust-mss command
specifies the MSS value on the intermediate router of the SYN packets to
avoid truncation.
俺太懒了就不翻译了。。自己慢慢看
[转自:http://www.net130.com/CMS/Pub/network/network_protocal/2005_09_22_97176.htm]




