1 17 package org.alfresco.filesys.smb.server; 18 19 import java.io.IOException ; 20 21 import org.alfresco.filesys.netbios.RFCNetBIOSProtocol; 22 import org.alfresco.filesys.server.auth.InvalidUserException; 23 import org.alfresco.filesys.server.auth.SrvAuthenticator; 24 import org.alfresco.filesys.server.core.InvalidDeviceInterfaceException; 25 import org.alfresco.filesys.server.core.ShareType; 26 import org.alfresco.filesys.server.core.SharedDevice; 27 import org.alfresco.filesys.server.filesys.AccessDeniedException; 28 import org.alfresco.filesys.server.filesys.AccessMode; 29 import org.alfresco.filesys.server.filesys.DirectoryNotEmptyException; 30 import org.alfresco.filesys.server.filesys.DiskDeviceContext; 31 import org.alfresco.filesys.server.filesys.DiskInterface; 32 import org.alfresco.filesys.server.filesys.FileAccess; 33 import org.alfresco.filesys.server.filesys.FileAction; 34 import org.alfresco.filesys.server.filesys.FileAttribute; 35 import org.alfresco.filesys.server.filesys.FileExistsException; 36 import org.alfresco.filesys.server.filesys.FileInfo; 37 import org.alfresco.filesys.server.filesys.FileName; 38 import org.alfresco.filesys.server.filesys.FileOpenParams; 39 import org.alfresco.filesys.server.filesys.FileSharingException; 40 import org.alfresco.filesys.server.filesys.FileStatus; 41 import org.alfresco.filesys.server.filesys.NetworkFile; 42 import org.alfresco.filesys.server.filesys.SearchContext; 43 import org.alfresco.filesys.server.filesys.SrvDiskInfo; 44 import org.alfresco.filesys.server.filesys.TooManyConnectionsException; 45 import org.alfresco.filesys.server.filesys.TooManyFilesException; 46 import org.alfresco.filesys.server.filesys.TreeConnection; 47 import org.alfresco.filesys.server.filesys.VolumeInfo; 48 import org.alfresco.filesys.smb.Capability; 49 import org.alfresco.filesys.smb.DataType; 50 import org.alfresco.filesys.smb.InvalidUNCPathException; 51 import org.alfresco.filesys.smb.PCShare; 52 import org.alfresco.filesys.smb.PacketType; 53 import org.alfresco.filesys.smb.SMBDate; 54 import org.alfresco.filesys.smb.SMBStatus; 55 import org.alfresco.filesys.util.DataPacker; 56 import org.alfresco.filesys.util.WildCard; 57 import org.apache.commons.logging.Log; 58 import org.apache.commons.logging.LogFactory; 59 60 63 class CoreProtocolHandler extends ProtocolHandler 64 { 65 66 68 private static final Log logger = LogFactory.getLog("org.alfresco.smb.protocol"); 69 70 72 private static final int RESUME_START = 0x00008003; 73 private static final int RESUME_DOT = 0x00008002; 74 private static final int RESUME_DOTDOT = 0x00008001; 75 76 78 private static final int MaxWordValue = 0x0000FFFF; 79 80 82 protected SMBSrvPacket m_smbPkt; 83 84 87 protected CoreProtocolHandler() 88 { 89 } 90 91 96 protected CoreProtocolHandler(SMBSrvSession sess) 97 { 98 super(sess); 99 } 100 101 106 public String getName() 107 { 108 return "Core Protocol"; 109 } 110 111 116 protected final void MapExceptionToSMBError(Exception ex) 117 { 118 119 } 120 121 132 protected final int packSearchInfo(byte[] buf, int bufPos, String searchStr, int resumeId, int searchId, 133 FileInfo info) 134 { 135 136 138 CoreResumeKey.putResumeKey(buf, bufPos, searchStr, resumeId + (searchId << 16)); 139 bufPos += CoreResumeKey.LENGTH; 140 141 143 buf[bufPos++] = (byte) (info.getFileAttributes() & 0x00FF); 144 145 SMBDate dateTime = new SMBDate(info.getModifyDateTime()); 146 if (dateTime != null) 147 { 148 DataPacker.putIntelShort(dateTime.asSMBTime(), buf, bufPos); 149 DataPacker.putIntelShort(dateTime.asSMBDate(), buf, bufPos + 2); 150 } 151 else 152 { 153 DataPacker.putIntelShort(0, buf, bufPos); 154 DataPacker.putIntelShort(0, buf, bufPos + 2); 155 } 156 bufPos += 4; 157 158 DataPacker.putIntelInt((int) info.getSize(), buf, bufPos); 159 bufPos += 4; 160 161 StringBuffer strBuf = new StringBuffer (); 162 strBuf.append(info.getFileName()); 163 164 while (strBuf.length() < 13) 165 strBuf.append('\0'); 166 167 if (strBuf.length() > 12) 168 strBuf.setLength(12); 169 170 DataPacker.putString(strBuf.toString().toUpperCase(), buf, bufPos, true); 171 bufPos += 13; 172 173 175 return bufPos; 176 } 177 178 185 protected void procCheckDirectory(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 186 { 187 188 190 if (m_smbPkt.checkPacketIsValid(0, 2) == false) 191 { 192 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 193 return; 194 } 195 196 199 int treeId = m_smbPkt.getTreeId(); 200 TreeConnection conn = m_sess.findConnection(treeId); 201 202 if (conn == null) 203 { 204 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 205 return; 206 } 207 208 210 if (conn.hasReadAccess() == false) 211 { 212 213 215 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 216 return; 217 } 218 219 221 int dataPos = m_smbPkt.getByteOffset(); 222 int dataLen = m_smbPkt.getByteCount(); 223 byte[] buf = m_smbPkt.getBuffer(); 224 225 227 String dirName = DataPacker.getDataString(DataType.ASCII, buf, dataPos, dataLen, m_smbPkt.isUnicode()); 228 if (dirName == null) 229 { 230 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 231 return; 232 } 233 234 236 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 237 logger.debug("Directory Check [" + treeId + "] name=" + dirName); 238 239 241 try 242 { 243 244 246 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 247 248 250 if (disk.fileExists(m_sess, conn, dirName) == FileStatus.DirectoryExists) 251 { 252 253 255 outPkt.setParameterCount(0); 256 outPkt.setByteCount(0); 257 258 260 m_sess.sendResponseSMB(outPkt); 261 } 262 else 263 { 264 265 270 m_sess.sendErrorResponseSMB(SMBStatus.DOSDirectoryInvalid, SMBStatus.ErrDos); 271 } 272 } 273 catch (InvalidDeviceInterfaceException ex) 274 { 275 276 278 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 279 return; 280 } 281 catch (java.io.IOException ex) 282 { 283 284 286 m_sess.sendErrorResponseSMB(SMBStatus.DOSDirectoryInvalid, SMBStatus.ErrDos); 287 return; 288 } 289 } 290 291 298 protected void procCloseFile(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 299 { 300 301 303 if (m_smbPkt.checkPacketIsValid(3, 0) == false) 304 { 305 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 306 return; 307 } 308 309 312 int treeId = m_smbPkt.getTreeId(); 313 TreeConnection conn = m_sess.findConnection(treeId); 314 315 if (conn == null) 316 { 317 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 318 return; 319 } 320 321 323 if (conn.hasReadAccess() == false) 324 { 325 326 328 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 329 return; 330 } 331 332 334 int fid = m_smbPkt.getParameter(0); 335 int ftime = m_smbPkt.getParameter(1); 336 int fdate = m_smbPkt.getParameter(2); 337 338 NetworkFile netFile = conn.findFile(fid); 339 340 if (netFile == null) 341 { 342 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidHandle, SMBStatus.ErrDos); 343 return; 344 } 345 346 348 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 349 logger.debug("File close [" + treeId + "] fid=" + fid); 350 351 353 try 354 { 355 356 358 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 359 360 364 if (disk != null) 365 disk.closeFile(m_sess, conn, netFile); 366 367 369 netFile.setClosed(true); 370 } 371 catch (InvalidDeviceInterfaceException ex) 372 { 373 374 376 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 377 return; 378 } 379 catch (java.io.IOException ex) 380 { 381 } 382 383 385 conn.removeFile(fid, getSession()); 386 387 389 outPkt.setParameterCount(0); 390 outPkt.setByteCount(0); 391 392 394 m_sess.sendResponseSMB(outPkt); 395 } 396 397 404 protected void procCreateDirectory(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 405 { 406 407 409 if (m_smbPkt.checkPacketIsValid(0, 2) == false) 410 { 411 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 412 return; 413 } 414 415 418 int treeId = m_smbPkt.getTreeId(); 419 TreeConnection conn = m_sess.findConnection(treeId); 420 421 if (conn == null) 422 { 423 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 424 return; 425 } 426 427 429 if (conn.hasWriteAccess() == false) 430 { 431 432 434 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 435 return; 436 } 437 438 440 int dataPos = m_smbPkt.getByteOffset(); 441 int dataLen = m_smbPkt.getByteCount(); 442 byte[] buf = m_smbPkt.getBuffer(); 443 444 446 String dirName = DataPacker.getDataString(DataType.ASCII, buf, dataPos, dataLen, m_smbPkt.isUnicode()); 447 if (dirName == null) 448 { 449 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 450 return; 451 } 452 453 455 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 456 logger.debug("Directory Create [" + treeId + "] name=" + dirName); 457 458 460 try 461 { 462 463 465 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 466 467 469 FileOpenParams params = new FileOpenParams(dirName, FileAction.CreateNotExist, AccessMode.ReadWrite, 470 FileAttribute.NTDirectory); 471 472 474 disk.createDirectory(m_sess, conn, params); 475 } 476 catch (InvalidDeviceInterfaceException ex) 477 { 478 479 481 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 482 return; 483 } 484 catch (FileExistsException ex) 485 { 486 487 489 m_sess.sendErrorResponseSMB(SMBStatus.NTObjectNameCollision, SMBStatus.DOSFileAlreadyExists, 490 SMBStatus.ErrDos); 491 return; 492 } 493 catch (AccessDeniedException ex) 494 { 495 496 498 m_sess.sendErrorResponseSMB(SMBStatus.NTAccessDenied, SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 499 return; 500 } 501 catch (java.io.IOException ex) 502 { 503 504 506 m_sess.sendErrorResponseSMB(SMBStatus.DOSDirectoryInvalid, SMBStatus.ErrDos); 507 return; 508 } 509 510 512 outPkt.setParameterCount(0); 513 outPkt.setByteCount(0); 514 515 517 m_sess.sendResponseSMB(outPkt); 518 } 519 520 527 protected void procCreateFile(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 528 { 529 530 532 if (m_smbPkt.checkPacketIsValid(3, 2) == false) 533 { 534 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 535 return; 536 } 537 538 541 int treeId = m_smbPkt.getTreeId(); 542 TreeConnection conn = m_sess.findConnection(treeId); 543 544 if (conn == null) 545 { 546 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 547 return; 548 } 549 550 552 if (conn.hasWriteAccess() == false) 553 { 554 555 557 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 558 return; 559 } 560 561 563 int dataPos = m_smbPkt.getByteOffset(); 564 int dataLen = m_smbPkt.getByteCount(); 565 byte[] buf = m_smbPkt.getBuffer(); 566 567 569 String fileName = DataPacker.getDataString(DataType.ASCII, buf, dataPos, dataLen, m_smbPkt.isUnicode()); 570 if (fileName == null) 571 { 572 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 573 return; 574 } 575 576 578 int attr = m_smbPkt.getParameter(0); 579 580 582 FileOpenParams params = new FileOpenParams(fileName, FileAction.CreateNotExist, AccessMode.ReadWrite, attr); 583 584 586 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 587 logger.debug("File Create [" + treeId + "] params=" + params); 588 589 591 int fid; 592 NetworkFile netFile = null; 593 594 try 595 { 596 597 599 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 600 601 603 netFile = disk.createFile(m_sess, conn, params); 604 605 607 fid = conn.addFile(netFile, getSession()); 608 } 609 catch (InvalidDeviceInterfaceException ex) 610 { 611 612 614 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 615 return; 616 } 617 catch (TooManyFilesException ex) 618 { 619 620 622 m_sess.sendErrorResponseSMB(SMBStatus.DOSTooManyOpenFiles, SMBStatus.ErrDos); 623 return; 624 } 625 catch (FileExistsException ex) 626 { 627 628 630 m_sess.sendErrorResponseSMB(SMBStatus.DOSFileAlreadyExists, SMBStatus.ErrDos); 631 return; 632 } 633 catch (java.io.IOException ex) 634 { 635 636 638 m_sess.sendErrorResponseSMB(SMBStatus.DOSFileNotFound, SMBStatus.ErrDos); 639 return; 640 } 641 642 644 outPkt.setParameterCount(1); 645 outPkt.setParameter(0, fid); 646 outPkt.setByteCount(0); 647 648 650 m_sess.sendResponseSMB(outPkt); 651 } 652 653 660 protected void procCreateTemporaryFile(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 661 { 662 663 } 664 665 672 protected void procDeleteDirectory(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 673 { 674 675 677 if (m_smbPkt.checkPacketIsValid(0, 2) == false) 678 { 679 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 680 return; 681 } 682 683 686 int treeId = m_smbPkt.getTreeId(); 687 TreeConnection conn = m_sess.findConnection(treeId); 688 689 if (conn == null) 690 { 691 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 692 return; 693 } 694 695 697 if (conn.hasWriteAccess() == false) 698 { 699 700 702 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 703 return; 704 } 705 706 708 int dataPos = m_smbPkt.getByteOffset(); 709 int dataLen = m_smbPkt.getByteCount(); 710 byte[] buf = m_smbPkt.getBuffer(); 711 712 714 String dirName = DataPacker.getDataString(DataType.ASCII, buf, dataPos, dataLen, m_smbPkt.isUnicode()); 715 716 if (dirName == null) 717 { 718 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 719 return; 720 } 721 722 724 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 725 logger.debug("Directory Delete [" + treeId + "] name=" + dirName); 726 727 729 try 730 { 731 732 734 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 735 736 738 disk.deleteDirectory(m_sess, conn, dirName); 739 } 740 catch (InvalidDeviceInterfaceException ex) 741 { 742 743 745 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 746 return; 747 } 748 catch (AccessDeniedException ex) 749 { 750 751 753 m_sess.sendErrorResponseSMB(SMBStatus.NTAccessDenied, SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 754 return; 755 } 756 catch (DirectoryNotEmptyException ex) 757 { 758 759 761 m_sess.sendErrorResponseSMB(SMBStatus.DOSDirectoryNotEmpty, SMBStatus.ErrDos); 762 return; 763 } 764 catch (java.io.IOException ex) 765 { 766 767 769 m_sess.sendErrorResponseSMB(SMBStatus.DOSDirectoryInvalid, SMBStatus.ErrDos); 770 return; 771 } 772 773 775 outPkt.setParameterCount(0); 776 outPkt.setByteCount(0); 777 778 780 m_sess.sendResponseSMB(outPkt); 781 } 782 783 790 protected void procDeleteFile(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 791 { 792 793 795 if (m_smbPkt.checkPacketIsValid(1, 2) == false) 796 { 797 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 798 return; 799 } 800 801 804 int treeId = m_smbPkt.getTreeId(); 805 TreeConnection conn = m_sess.findConnection(treeId); 806 807 if (conn == null) 808 { 809 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 810 return; 811 } 812 813 815 if (conn.hasWriteAccess() == false) 816 { 817 818 820 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 821 return; 822 } 823 824 826 int dataPos = m_smbPkt.getByteOffset(); 827 int dataLen = m_smbPkt.getByteCount(); 828 byte[] buf = m_smbPkt.getBuffer(); 829 830 832 String fileName = DataPacker.getDataString(DataType.ASCII, buf, dataPos, dataLen, m_smbPkt.isUnicode()); 833 if (fileName == null) 834 { 835 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 836 return; 837 } 838 839 841 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 842 logger.debug("File Delete [" + treeId + "] name=" + fileName); 843 844 846 int fid; 847 NetworkFile netFile = null; 848 849 try 850 { 851 852 854 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 855 856 858 disk.deleteFile(m_sess, conn, fileName); 859 } 860 catch (InvalidDeviceInterfaceException ex) 861 { 862 863 865 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 866 return; 867 } 868 catch (java.io.IOException ex) 869 { 870 871 873 m_sess.sendErrorResponseSMB(SMBStatus.DOSFileNotFound, SMBStatus.ErrDos); 874 return; 875 } 876 877 879 outPkt.setParameterCount(0); 880 outPkt.setByteCount(0); 881 882 884 m_sess.sendResponseSMB(outPkt); 885 } 886 887 894 protected void procDiskAttributes(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 895 { 896 897 899 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_INFO)) 900 logger.debug("Get disk attributes"); 901 902 904 if (m_smbPkt.getParameterCount() != 0 && m_smbPkt.getByteCount() != 0) 905 { 906 907 909 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 910 return; 911 } 912 913 915 int treeId = m_smbPkt.getTreeId(); 916 TreeConnection conn = m_sess.findConnection(treeId); 917 918 if (conn == null) 919 { 920 m_sess.sendErrorResponseSMB(SMBStatus.SRVInvalidTID, SMBStatus.ErrSrv); 921 return; 922 } 923 924 926 if (conn.hasReadAccess() == false) 927 { 928 929 931 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 932 return; 933 } 934 935 937 DiskInterface disk = null; 938 DiskDeviceContext diskCtx = null; 939 940 try 941 { 942 disk = (DiskInterface) conn.getSharedDevice().getInterface(); 943 diskCtx = (DiskDeviceContext) conn.getContext(); 944 } 945 catch (InvalidDeviceInterfaceException ex) 946 { 947 948 950 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 951 return; 952 } 953 954 956 SrvDiskInfo diskInfo = getDiskInformation(disk, diskCtx); 957 958 960 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_INFO)) 961 logger.debug(" Disk info - total=" + diskInfo.getTotalUnits() + ", free=" + diskInfo.getFreeUnits() 962 + ", blocksPerUnit=" + diskInfo.getBlocksPerAllocationUnit() + ", blockSize=" 963 + diskInfo.getBlockSize()); 964 965 967 long totUnits = diskInfo.getTotalUnits(); 968 long freeUnits = diskInfo.getFreeUnits(); 969 int blocksUnit = diskInfo.getBlocksPerAllocationUnit(); 970 971 while (totUnits > MaxWordValue && blocksUnit <= MaxWordValue) 972 { 973 974 976 blocksUnit *= 2; 977 978 totUnits = totUnits / 2L; 979 freeUnits = freeUnits / 2L; 980 } 981 982 984 if (totUnits > MaxWordValue || blocksUnit > MaxWordValue) 985 { 986 987 989 totUnits = MaxWordValue; 990 991 if (freeUnits > MaxWordValue) 992 freeUnits = MaxWordValue / 2; 993 994 if (blocksUnit > MaxWordValue) 995 blocksUnit = MaxWordValue; 996 } 997 998 1000 outPkt.setParameterCount(5); 1001 1002 outPkt.setParameter(0, (int) totUnits); 1003 outPkt.setParameter(1, blocksUnit); 1004 outPkt.setParameter(2, diskInfo.getBlockSize()); 1005 outPkt.setParameter(3, (int) freeUnits); 1006 outPkt.setParameter(4, 0); 1007 1008 outPkt.setByteCount(0); 1009 1010 1012 m_sess.sendResponseSMB(outPkt); 1013 } 1014 1015 1022 protected void procEcho(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 1023 { 1024 1025 1027 if (m_smbPkt.checkPacketIsValid(1, 0) == false) 1028 { 1029 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 1030 return; 1031 } 1032 1033 1035 int echoCnt = m_smbPkt.getParameter(0); 1036 1037 1039 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_ECHO)) 1040 logger.debug("Echo - Count = " + echoCnt); 1041 1042 1044 int echoSeq = 1; 1045 1046 while (echoCnt > 0) 1047 { 1048 1049 1051 outPkt.setParameter(0, echoSeq++); 1052 1053 1055 m_sess.sendResponseSMB(outPkt); 1056 echoCnt--; 1057 1058 1060 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_ECHO)) 1061 logger.debug("Echo Packet, Seq = " + echoSeq); 1062 } 1063 } 1064 1065 1072 protected void procFlushFile(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 1073 { 1074 1075 1077 if (m_smbPkt.checkPacketIsValid(1, 0) == false) 1078 { 1079 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 1080 return; 1081 } 1082 1083 1086 int treeId = m_smbPkt.getTreeId(); 1087 TreeConnection conn = m_sess.findConnection(treeId); 1088 1089 if (conn == null) 1090 { 1091 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 1092 return; 1093 } 1094 1095 1097 if (conn.hasWriteAccess() == false) 1098 { 1099 1100 1102 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 1103 return; 1104 } 1105 1106 1108 int fid = m_smbPkt.getParameter(0); 1109 1110 NetworkFile netFile = conn.findFile(fid); 1111 1112 if (netFile == null) 1113 { 1114 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidHandle, SMBStatus.ErrDos); 1115 return; 1116 } 1117 1118 1120 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 1121 logger.debug("File Flush [" + netFile.getFileId() + "]"); 1122 1123 1125 try 1126 { 1127 1128 1130 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 1131 1132 1134 disk.flushFile(m_sess, conn, netFile); 1135 } 1136 catch (InvalidDeviceInterfaceException ex) 1137 { 1138 1139 1141 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 1142 return; 1143 } 1144 catch (java.io.IOException ex) 1145 { 1146 1147 1149 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 1150 logger.debug("File Flush Error [" + netFile.getFileId() + "] : " + ex.toString()); 1151 1152 1154 m_sess.sendErrorResponseSMB(SMBStatus.HRDWriteFault, SMBStatus.ErrHrd); 1155 return; 1156 } 1157 1158 1160 outPkt.setParameterCount(0); 1161 outPkt.setByteCount(0); 1162 1163 m_sess.sendResponseSMB(outPkt); 1164 } 1165 1166 1173 protected void procGetFileAttributes(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 1174 { 1175 1176 1178 if (m_smbPkt.checkPacketIsValid(0, 2) == false) 1179 { 1180 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 1181 return; 1182 } 1183 1184 1187 int treeId = m_smbPkt.getTreeId(); 1188 TreeConnection conn = m_sess.findConnection(treeId); 1189 1190 if (conn == null) 1191 { 1192 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 1193 return; 1194 } 1195 1196 1198 if (conn.hasReadAccess() == false) 1199 { 1200 1201 1203 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 1204 return; 1205 } 1206 1207 1209 int dataPos = m_smbPkt.getByteOffset(); 1210 int dataLen = m_smbPkt.getByteCount(); 1211 byte[] buf = m_smbPkt.getBuffer(); 1212 1213 1215 String fileName = DataPacker.getDataString(DataType.ASCII, buf, dataPos, dataLen, m_smbPkt.isUnicode()); 1216 if (fileName == null) 1217 { 1218 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 1219 return; 1220 } 1221 1222 1224 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 1225 logger.debug("Get File Information [" + treeId + "] name=" + fileName); 1226 1227 1229 try 1230 { 1231 1232 1234 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 1235 1236 1238 FileInfo finfo = disk.getFileInformation(m_sess, conn, fileName); 1239 if (finfo != null) 1240 { 1241 1242 1244 if (conn.getSharedDevice().isReadOnly() && finfo.isReadOnly() == false) 1245 { 1246 1247 1249 finfo.setFileAttributes(finfo.getFileAttributes() + FileAttribute.ReadOnly); 1250 } 1251 1252 1254 outPkt.setParameterCount(10); 1255 outPkt.setParameter(0, finfo.getFileAttributes()); 1256 if (finfo.getModifyDateTime() != 0L) 1257 { 1258 SMBDate dateTime = new SMBDate(finfo.getModifyDateTime()); 1259 outPkt.setParameter(1, dateTime.asSMBTime()); 1260 outPkt.setParameter(2, dateTime.asSMBDate()); 1261 } 1262 else 1263 { 1264 outPkt.setParameter(1, 0); 1265 outPkt.setParameter(2, 0); 1266 } 1267 outPkt.setParameter(3, (int) finfo.getSize() & 0x0000FFFF); 1268 outPkt.setParameter(4, (int) (finfo.getSize() & 0xFFFF0000) >> 16); 1269 1270 for (int i = 5; i < 10; i++) 1271 outPkt.setParameter(i, 0); 1272 1273 outPkt.setByteCount(0); 1274 1275 1277 m_sess.sendResponseSMB(outPkt); 1278 return; 1279 } 1280 } 1281 catch (InvalidDeviceInterfaceException ex) 1282 { 1283 1284 1286 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 1287 return; 1288 } 1289 catch (java.io.IOException ex) 1290 { 1291 } 1292 1293 1295 m_sess.sendErrorResponseSMB(SMBStatus.DOSFileNotFound, SMBStatus.ErrDos); 1296 } 1297 1298 1305 protected void procGetFileInformation(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 1306 { 1307 1308 1310 if (m_smbPkt.checkPacketIsValid(1, 0) == false) 1311 { 1312 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 1313 return; 1314 } 1315 1316 1319 int treeId = m_smbPkt.getTreeId(); 1320 TreeConnection conn = m_sess.findConnection(treeId); 1321 1322 if (conn == null) 1323 { 1324 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 1325 return; 1326 } 1327 1328 1330 if (conn.hasReadAccess() == false) 1331 { 1332 1333 1335 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 1336 return; 1337 } 1338 1339 1341 int fid = m_smbPkt.getParameter(0); 1342 NetworkFile netFile = conn.findFile(fid); 1343 1344 if (netFile == null) 1345 { 1346 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidHandle, SMBStatus.ErrDos); 1347 return; 1348 } 1349 1350 1352 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 1353 logger.debug("Get File Information 2 [" + netFile.getFileId() + "]"); 1354 1355 1357 try 1358 { 1359 1360 1362 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 1363 1364 1366 FileInfo finfo = disk.getFileInformation(m_sess, conn, netFile.getFullName()); 1367 if (finfo != null) 1368 { 1369 1370 1372 if (conn.getSharedDevice().isReadOnly() && finfo.isReadOnly() == false) 1373 { 1374 1375 1377 finfo.setFileAttributes(finfo.getFileAttributes() + FileAttribute.ReadOnly); 1378 } 1379 1380 1382 outPkt.setParameterCount(11); 1383 outPkt.setByteCount(0); 1384 1385 1389 SMBDate dateTime = new SMBDate(0); 1390 1391 if (finfo.getCreationDateTime() != 0L) 1392 { 1393 dateTime.setTime(finfo.getCreationDateTime()); 1394 outPkt.setParameter(0, dateTime.asSMBDate()); 1395 outPkt.setParameter(1, dateTime.asSMBTime()); 1396 } 1397 else 1398 { 1399 outPkt.setParameter(0, 0); 1400 outPkt.setParameter(1, 0); 1401 } 1402 1403 1405 if (finfo.getAccessDateTime() != 0L) 1406 { 1407 dateTime.setTime(finfo.getAccessDateTime()); 1408 outPkt.setParameter(2, dateTime.asSMBDate()); 1409 outPkt.setParameter(3, dateTime.asSMBTime()); 1410 } 1411 else 1412 { 1413 outPkt.setParameter(2, 0); 1414 outPkt.setParameter(3, 0); 1415 } 1416 1417 1419 if (finfo.getModifyDateTime() != 0L) 1420 { 1421 dateTime.setTime(finfo.getModifyDateTime()); 1422 outPkt.setParameter(4, dateTime.asSMBDate()); 1423 outPkt.setParameter(5, dateTime.asSMBTime()); 1424 } 1425 else 1426 { 1427 outPkt.setParameter(4, 0); 1428 outPkt.setParameter(5, 0); 1429 } 1430 1431 1433 outPkt.setParameter(6, (int) finfo.getSize() & 0x0000FFFF); 1434 outPkt.setParameter(7, (int) (finfo.getSize() & 0xFFFF0000) >> 16); 1435 1436 1438 outPkt.setParameter(8, (int) finfo.getSize() & 0x0000FFFF); 1439 outPkt.setParameter(9, (int) (finfo.getSize() & 0xFFFF0000) >> 16); 1440 1441 1443 outPkt.setParameter(10, finfo.getFileAttributes()); 1444 1445 1447 m_sess.sendResponseSMB(outPkt); 1448 return; 1449 } 1450 } 1451 catch (InvalidDeviceInterfaceException ex) 1452 { 1453 1454 1456 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 1457 return; 1458 } 1459 catch (java.io.IOException ex) 1460 { 1461 } 1462 1463 1465 m_sess.sendErrorResponseSMB(SMBStatus.DOSFileNotFound, SMBStatus.ErrDos); 1466 } 1467 1468 1473 protected void procLockFile(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 1474 { 1475 1476 1478 if (m_smbPkt.checkPacketIsValid(5, 0) == false) 1479 { 1480 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 1481 return; 1482 } 1483 1484 1487 int treeId = m_smbPkt.getTreeId(); 1488 TreeConnection conn = m_sess.findConnection(treeId); 1489 1490 if (conn == null) 1491 { 1492 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 1493 return; 1494 } 1495 1496 1498 if (conn.hasReadAccess() == false) 1499 { 1500 1501 1503 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 1504 return; 1505 } 1506 1507 1509 int fid = m_smbPkt.getParameter(0); 1510 long lockcnt = m_smbPkt.getParameterLong(1); 1511 long lockoff = m_smbPkt.getParameterLong(3); 1512 1513 NetworkFile netFile = conn.findFile(fid); 1514 1515 if (netFile == null) 1516 { 1517 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidHandle, SMBStatus.ErrDos); 1518 return; 1519 } 1520 1521 1523 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILEIO)) 1524 logger.debug("File Lock [" + netFile.getFileId() + "] : Offset=" + lockoff + " ,Count=" + lockcnt); 1525 1526 1530 outPkt.setParameterCount(0); 1531 outPkt.setByteCount(0); 1532 1533 1535 m_sess.sendResponseSMB(outPkt); 1536 } 1537 1538 1545 protected void procOpenFile(SMBSrvPacket outPkt) throws IOException , SMBSrvException 1546 { 1547 1548 1550 if (m_smbPkt.checkPacketIsValid(2, 2) == false) 1551 { 1552 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 1553 return; 1554 } 1555 1556 1559 int treeId = m_smbPkt.getTreeId(); 1560 TreeConnection conn = m_sess.findConnection(treeId); 1561 1562 if (conn == null) 1563 { 1564 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 1565 return; 1566 } 1567 1568 1570 if (conn.hasReadAccess() == false) 1571 { 1572 1573 1575 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 1576 return; 1577 } 1578 1579 1581 int dataPos = m_smbPkt.getByteOffset(); 1582 int dataLen = m_smbPkt.getByteCount(); 1583 byte[] buf = m_smbPkt.getBuffer(); 1584 1585 1587 String fileName = DataPacker.getDataString(DataType.ASCII, buf, dataPos, dataLen, m_smbPkt.isUnicode()); 1588 if (fileName == null) 1589 { 1590 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 1591 return; 1592 } 1593 1594 1596 int mode = m_smbPkt.getParameter(0); 1597 int attr = m_smbPkt.getParameter(1); 1598 1599 1601 FileOpenParams params = new FileOpenParams(fileName, mode, AccessMode.ReadWrite, attr); 1602 1604 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 1605 logger.debug("File Open [" + treeId + "] params=" + params); 1606 1607 1609 int fid; 1610 NetworkFile netFile = null; 1611 1612 try 1613 { 1614 1615 1617 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 1618 1619 1621 netFile = disk.openFile(m_sess, conn, params); 1622 1623 1625 fid = conn.addFile(netFile, getSession()); 1626 } 1627 catch (InvalidDeviceInterfaceException ex) 1628 { 1629 1630 1632 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 1633 return; 1634 } 1635 catch (TooManyFilesException ex) 1636 { 1637 1638 1640 m_sess.sendErrorResponseSMB(SMBStatus.DOSTooManyOpenFiles, SMBStatus.ErrDos); 1641 return; 1642 } 1643 catch (AccessDeniedException ex) 1644 { 1645 1646 1648 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 1649 return; 1650 } 1651 catch (FileSharingException ex) 1652 { 1653 1654 1656 m_sess.sendErrorResponseSMB(SMBStatus.DOSFileSharingConflict, SMBStatus.ErrDos); 1657 return; 1658 } 1659 catch (java.io.IOException ex) 1660 { 1661 1662 1664 m_sess.sendErrorResponseSMB(SMBStatus.DOSFileNotFound, SMBStatus.ErrDos); 1665 return; 1666 } 1667 1668 1670 outPkt.setParameterCount(7); 1671 1672 outPkt.setParameter(0, fid); 1673 outPkt.setParameter(1, 0); 1675 if (netFile.hasModifyDate()) 1676 { 1677 outPkt.setParameterLong(2, (int) (netFile.getModifyDate() / 1000L)); 1678 1679 } 1683 else 1684 outPkt.setParameterLong(2, 0); 1685 1686 outPkt.setParameterLong(4, netFile.getFileSizeInt()); outPkt.setParameter(6, netFile.getGrantedAccess()); 1688 1689 outPkt.setByteCount(0); 1690 1691 1693 m_sess.sendResponseSMB(outPkt); 1694 } 1695 1696 1703 protected void procProcessExit(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 1704 { 1705 1706 1708 if (m_smbPkt.checkPacketIsValid(0, 0) == false) 1709 { 1710 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 1711 return; 1712 } 1713 1714 1717 int treeId = m_smbPkt.getTreeId(); 1718 TreeConnection conn = m_sess.findConnection(treeId); 1719 1720 if (conn == null) 1721 { 1722 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 1723 return; 1724 } 1725 1726 1728 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 1729 logger.debug("Process Exit - Open files = " + conn.openFileCount()); 1730 1731 1733 if (conn.openFileCount() > 0) 1734 { 1735 1736 1738 conn.closeConnection(getSession()); 1739 } 1740 1741 1743 outPkt.setParameterCount(0); 1744 outPkt.setByteCount(0); 1745 1746 1748 m_sess.sendResponseSMB(outPkt); 1749 } 1750 1751 1758 protected void procReadFile(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 1759 { 1760 1761 1763 if (m_smbPkt.checkPacketIsValid(5, 0) == false) 1764 { 1765 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 1766 return; 1767 } 1768 1769 1772 int treeId = m_smbPkt.getTreeId(); 1773 TreeConnection conn = m_sess.findConnection(treeId); 1774 1775 if (conn == null) 1776 { 1777 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 1778 return; 1779 } 1780 1781 1783 if (conn.hasReadAccess() == false) 1784 { 1785 1786 1788 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 1789 return; 1790 } 1791 1792 1794 int fid = m_smbPkt.getParameter(0); 1795 int reqcnt = m_smbPkt.getParameter(1); 1796 int reqoff = m_smbPkt.getParameter(2) + (m_smbPkt.getParameter(3) << 16); 1797 1798 NetworkFile netFile = conn.findFile(fid); 1799 1800 if (netFile == null) 1801 { 1802 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidHandle, SMBStatus.ErrDos); 1803 return; 1804 } 1805 1806 1808 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILEIO)) 1809 logger.debug("File Read [" + netFile.getFileId() + "] : Size=" + reqcnt + " ,Pos=" + reqoff); 1810 1811 1813 byte[] buf = outPkt.getBuffer(); 1814 int rdlen = 0; 1815 1816 try 1817 { 1818 1819 1821 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 1822 1823 1825 int dataOff = outPkt.getByteOffset() + 3; 1826 int availCnt = buf.length - dataOff; 1827 if (m_sess.hasClientCapability(Capability.LargeRead) == false) 1828 availCnt = m_sess.getClientMaximumBufferSize() - dataOff; 1829 1830 if (availCnt < reqcnt) 1831 { 1832 1833 1835 reqcnt = availCnt; 1836 1837 1839 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILEIO)) 1840 logger.debug("File Read [" + netFile.getFileId() + "] Limited to " + availCnt); 1841 } 1842 1843 1845 rdlen = disk.readFile(m_sess, conn, netFile, buf, outPkt.getByteOffset() + 3, reqcnt, reqoff); 1846 } 1847 catch (InvalidDeviceInterfaceException ex) 1848 { 1849 1850 1852 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 1853 return; 1854 } 1855 catch (java.io.IOException ex) 1856 { 1857 1858 1860 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILEIO)) 1861 logger.debug("File Read Error [" + netFile.getFileId() + "] : " + ex.toString()); 1862 1863 1865 m_sess.sendErrorResponseSMB(SMBStatus.HRDReadFault, SMBStatus.ErrHrd); 1866 return; 1867 } 1868 1869 1871 int bytOff = outPkt.getByteOffset(); 1872 buf[bytOff] = (byte) DataType.DataBlock; 1873 DataPacker.putIntelShort(rdlen, buf, bytOff + 1); 1874 outPkt.setByteCount(rdlen + 3); 1876 outPkt.setParameter(0, rdlen); 1877 outPkt.setParameter(1, 0); 1878 outPkt.setParameter(2, 0); 1879 outPkt.setParameter(3, 0); 1880 outPkt.setParameter(4, 0); 1881 1882 1884 m_sess.sendResponseSMB(outPkt); 1885 } 1886 1887 1894 protected void procRenameFile(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 1895 { 1896 1897 1899 if (m_smbPkt.checkPacketIsValid(1, 4) == false) 1900 { 1901 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 1902 return; 1903 } 1904 1905 1908 int treeId = m_smbPkt.getTreeId(); 1909 TreeConnection conn = m_sess.findConnection(treeId); 1910 1911 if (conn == null) 1912 { 1913 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 1914 return; 1915 } 1916 1917 1919 if (conn.hasWriteAccess() == false) 1920 { 1921 1922 1924 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 1925 return; 1926 } 1927 1928 1930 int dataPos = m_smbPkt.getByteOffset(); 1931 int dataLen = m_smbPkt.getByteCount(); 1932 byte[] buf = m_smbPkt.getBuffer(); 1933 1934 1936 boolean isUni = m_smbPkt.isUnicode(); 1937 String oldName = DataPacker.getDataString(DataType.ASCII, buf, dataPos, dataLen, isUni); 1938 if (oldName == null) 1939 { 1940 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 1941 return; 1942 } 1943 1944 1946 if (isUni) 1947 { 1948 int len = (oldName.length() * 2) + 2; 1949 dataPos = DataPacker.wordAlign(dataPos + 1) + len; 1950 dataLen -= len; 1951 } 1952 else 1953 { 1954 dataPos += oldName.length() + 2; dataLen -= oldName.length() + 2; 1956 } 1957 1958 1960 String newName = DataPacker.getDataString(DataType.ASCII, buf, dataPos, dataLen, isUni); 1961 if (newName == null) 1962 { 1963 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 1964 return; 1965 } 1966 1967 1969 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 1970 logger.debug("File Rename [" + treeId + "] old name=" + oldName + ", new name=" + newName); 1971 1972 1974 int fid; 1975 NetworkFile netFile = null; 1976 1977 try 1978 { 1979 1980 1982 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 1983 1984 1986 disk.renameFile(m_sess, conn, oldName, newName); 1987 } 1988 catch (InvalidDeviceInterfaceException ex) 1989 { 1990 1991 1993 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 1994 return; 1995 } 1996 catch (java.io.IOException ex) 1997 { 1998 1999 2001 m_sess.sendErrorResponseSMB(SMBStatus.DOSFileNotFound, SMBStatus.ErrDos); 2002 return; 2003 } 2004 2005 2007 outPkt.setParameterCount(0); 2008 outPkt.setByteCount(0); 2009 2010 2012 m_sess.sendResponseSMB(outPkt); 2013 } 2014 2015 2022 protected final void procSearch(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 2023 { 2024 2025 2027 if (m_smbPkt.checkPacketIsValid(2, 5) == false) 2028 { 2029 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 2030 return; 2031 } 2032 2033 2035 int treeId = m_smbPkt.getTreeId(); 2036 TreeConnection conn = m_sess.findConnection(treeId); 2037 2038 if (conn == null) 2039 { 2040 m_sess.sendErrorResponseSMB(SMBStatus.SRVInvalidTID, SMBStatus.ErrSrv); 2041 return; 2042 } 2043 2044 2046 if (conn.hasReadAccess() == false) 2047 { 2048 2049 2051 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 2052 return; 2053 } 2054 2055 2057 int maxFiles = m_smbPkt.getParameter(0); 2058 int srchAttr = m_smbPkt.getParameter(1); 2059 2060 2062 if ((srchAttr & FileAttribute.Volume) != 0) 2063 { 2064 2065 2067 procSearchVolumeLabel(outPkt); 2068 return; 2069 } 2070 2071 2073 int dataPos = m_smbPkt.getByteOffset(); 2074 int dataLen = m_smbPkt.getByteCount(); 2075 byte[] buf = m_smbPkt.getBuffer(); 2076 2077 2079 String srchPath = DataPacker.getDataString(DataType.ASCII, buf, dataPos, dataLen, m_smbPkt.isUnicode()); 2080 2081 if (srchPath == null) 2082 { 2083 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidFunc, SMBStatus.ErrDos); 2084 return; 2085 } 2086 2087 2089 dataPos += srchPath.length() + 2; 2090 dataLen -= srchPath.length() + 2; 2091 2092 int resumeLen = 0; 2093 2094 if (buf[dataPos++] == DataType.VariableBlock) 2095 { 2096 2097 2099 resumeLen = DataPacker.getIntelShort(buf, dataPos); 2100 2101 2103 dataLen -= 3; dataPos += 2; 2106 2108 if (resumeLen > dataLen) 2109 { 2110 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 2111 return; 2112 } 2113 } 2114 2115 2117 SearchContext ctx = null; 2118 DiskInterface disk = null; 2119 2120 try 2121 { 2122 disk = (DiskInterface) conn.getSharedDevice().getInterface(); 2123 } 2124 catch (InvalidDeviceInterfaceException ex) 2125 { 2126 2127 2129 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 2130 return; 2131 } 2132 2133 2135 byte[] resumeKey = null; 2136 int searchId = -1; 2137 2138 2142 int resumeId = RESUME_START; 2143 2144 if (resumeLen == 0 && srchPath.length() > 0) 2145 { 2146 2147 2149 searchId = m_sess.allocateSearchSlot(); 2150 if (searchId == -1) 2151 { 2152 2153 2160 int idx = 0; 2161 ctx = m_sess.getSearchContext(idx); 2162 2163 while (ctx != null && searchId == -1) 2164 { 2165 2166 2168 if (ctx.getSearchString().compareTo("????????.???") == 0) 2169 { 2170 2171 2173 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_SEARCH)) 2174 logger.debug("Release leaked search [" + idx + "]"); 2175 2176 2178 m_sess.deallocateSearchSlot(idx); 2179 2180 2182 searchId = m_sess.allocateSearchSlot(); 2183 } 2184 else 2185 { 2186 2187 2189 ctx = m_sess.getSearchContext(++idx); 2190 } 2191 } 2192 2193 2195 if (searchId == -1) 2196 { 2197 2198 2200 m_sess.sendErrorResponseSMB(SMBStatus.SRVNoResourcesAvailable, SMBStatus.ErrSrv); 2201 return; 2202 } 2203 } 2204 2205 2207 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_SEARCH)) 2208 logger.debug("Start search [" + searchId + "] - " + srchPath + ", attr=0x" 2209 + Integer.toHexString(srchAttr) + ", maxFiles=" + maxFiles); 2210 2211 2213 ctx = disk.startSearch(m_sess, conn, srchPath, srchAttr); 2214 if (ctx != null) 2215 { 2216 2217 2219 ctx.setTreeId(treeId); 2220 ctx.setMaximumFiles(maxFiles); 2221 } 2222 2223 2225 m_sess.setSearchContext(searchId, ctx); 2226 } 2227 else 2228 { 2229 2230 2232 resumeKey = new byte[CoreResumeKey.LENGTH]; 2233 CoreResumeKey.getResumeKey(buf, dataPos, resumeKey); 2234 2235 2237 int id = CoreResumeKey.getServerArea(resumeKey, 0); 2238 searchId = (id & 0xFFFF0000) >> 16; 2239 ctx = m_sess.getSearchContext(searchId); 2240 2241 2243 if (ctx == null) 2244 { 2245 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 2246 return; 2247 } 2248 2249 2251 resumeId = id & 0x0000FFFF; 2252 2253 2256 if (resumeId < RESUME_DOTDOT && ctx.getResumeId() != resumeId) 2257 { 2258 2259 2261 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_SEARCH)) 2262 logger.debug("Search resume at " + resumeId); 2263 2264 2266 if (ctx.restartAt(resumeId) == false) 2267 { 2268 2269 2271 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_SEARCH)) 2272 logger.debug("Search restart failed"); 2273 2274 2276 m_sess.sendErrorResponseSMB(SMBStatus.DOSNoMoreFiles, SMBStatus.ErrDos); 2277 2278 2280 m_sess.deallocateSearchSlot(searchId); 2281 return; 2282 } 2283 } 2284 } 2285 2286 2288 if (ctx == null) 2289 { 2290 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 2291 return; 2292 } 2293 2294 2296 if (ctx.getTreeId() != treeId) 2297 { 2298 m_sess.sendErrorResponseSMB(SMBStatus.SRVInvalidTID, SMBStatus.ErrSrv); 2299 return; 2300 } 2301 2302 2304 outPkt.setParameterCount(1); 2305 int bufPos = outPkt.getByteOffset(); 2306 buf[bufPos] = (byte) DataType.VariableBlock; 2307 bufPos += 3; int fileCnt = 0; 2309 2310 2312 if ((srchAttr & FileAttribute.Directory) != 0 && resumeId >= RESUME_DOTDOT 2313 && WildCard.containsWildcards(srchPath)) 2314 { 2315 2316 2324 String workDir = FileName.removeFileName(srchPath); 2325 FileInfo dirInfo = disk.getFileInformation(m_sess, conn, workDir); 2326 2327 2329 if (dirInfo != null) 2330 dirInfo = new FileInfo(".", 0, FileAttribute.Directory); 2331 2332 2334 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_SEARCH)) 2335 logger.debug("Search adding . and .. entries: " + dirInfo.toString()); 2336 2337 2339 if (resumeId == RESUME_START) 2340 { 2341 2342 2344 dirInfo.setFileName("."); 2345 resumeId = RESUME_DOT; 2346 bufPos = packSearchInfo(buf, bufPos, ctx.getSearchString(), RESUME_DOT, searchId, dirInfo); 2347 2348 2350 fileCnt++; 2351 } 2352 2353 2355 if (resumeId == RESUME_DOT) 2356 { 2357 2358 2360 dirInfo.setFileName(".."); 2361 bufPos = packSearchInfo(buf, bufPos, ctx.getSearchString(), RESUME_DOTDOT, searchId, dirInfo); 2362 2363 2365 fileCnt++; 2366 } 2367 } 2368 2369 2371 FileInfo fileInfo = new FileInfo(); 2372 2373 while (fileCnt < ctx.getMaximumFiles() && ctx.nextFileInfo(fileInfo) == true) 2374 { 2375 2376 2380 if (fileInfo.getFileName().startsWith(".")) 2381 continue; 2382 2383 2385 resumeId = ctx.getResumeId(); 2386 2387 2389 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_SEARCH)) 2390 logger.debug("Search return file " + fileInfo.toString() + ", resumeId=" + resumeId); 2391 2392 2394 if (conn.getSharedDevice().isReadOnly() && fileInfo.isReadOnly() == false) 2395 { 2396 2397 2399 fileInfo.setFileAttributes(fileInfo.getFileAttributes() + FileAttribute.ReadOnly); 2400 } 2401 2402 2404 bufPos = packSearchInfo(buf, bufPos, ctx.getSearchString(), resumeId, searchId, fileInfo); 2405 2406 2408 fileCnt++; 2409 fileInfo.resetInfo(); 2410 } 2411 2412 2414 if (fileCnt == 0) 2415 { 2416 2417 2419 outPkt.setParameterCount(1); 2420 outPkt.setParameter(0, 0); 2421 outPkt.setByteCount(0); 2422 2423 outPkt.setErrorClass(SMBStatus.ErrDos); 2424 outPkt.setErrorCode(SMBStatus.DOSNoMoreFiles); 2425 2426 m_sess.sendResponseSMB(outPkt); 2427 2428 2430 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_SEARCH)) 2431 logger.debug("End search [" + searchId + "]"); 2432 2433 2435 m_sess.deallocateSearchSlot(searchId); 2436 } 2437 else 2438 { 2439 2440 2442 dataLen = bufPos - outPkt.getByteOffset(); 2443 outPkt.setByteCount(dataLen); 2444 2445 2447 bufPos = outPkt.getByteOffset() + 1; 2448 DataPacker.putIntelShort(dataLen - 3, buf, bufPos); 2449 outPkt.setParameter(0, fileCnt); 2450 2451 2453 m_sess.sendResponseSMB(outPkt); 2454 2455 2459 if (fileCnt == 1 && resumeLen == 0 && WildCard.containsWildcards(srchPath) == false) 2460 { 2461 2462 2464 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_SEARCH)) 2465 logger.debug("End search [" + searchId + "] (Not wildcard)"); 2466 2467 2469 m_sess.deallocateSearchSlot(searchId); 2470 } 2471 } 2472 } 2473 2474 2479 protected final void procSearchVolumeLabel(SMBSrvPacket outPkt) throws IOException , SMBSrvException 2480 { 2481 2482 2484 int treeId = m_smbPkt.getTreeId(); 2485 TreeConnection conn = m_sess.findConnection(treeId); 2486 2487 if (conn == null) 2488 { 2489 m_sess.sendErrorResponseSMB(SMBStatus.SRVInvalidTID, SMBStatus.ErrSrv); 2490 return; 2491 } 2492 2493 2495 if (conn.hasReadAccess() == false) 2496 { 2497 2498 2500 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 2501 return; 2502 } 2503 2504 2506 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_SEARCH)) 2507 logger.debug("Start Search - Volume Label"); 2508 2509 2511 DiskInterface disk = null; 2512 DiskDeviceContext diskCtx = null; 2513 2514 try 2515 { 2516 disk = (DiskInterface) conn.getSharedDevice().getInterface(); 2517 diskCtx = (DiskDeviceContext) conn.getContext(); 2518 } 2519 catch (InvalidDeviceInterfaceException ex) 2520 { 2521 2522 2524 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 2525 return; 2526 } 2527 2528 2530 VolumeInfo volInfo = diskCtx.getVolumeInformation(); 2531 String volLabel = ""; 2532 if (volInfo != null) 2533 volLabel = volInfo.getVolumeLabel(); 2534 2535 2537 outPkt.setParameterCount(1); 2538 int bufPos = outPkt.getByteOffset(); 2539 byte[] buf = outPkt.getBuffer(); 2540 buf[bufPos++] = (byte) DataType.VariableBlock; 2541 2542 2544 int dataLen = CoreResumeKey.LENGTH + 22; 2545 DataPacker.putIntelShort(dataLen, buf, bufPos); 2546 bufPos += 2; 2547 2548 2550 CoreResumeKey.putResumeKey(buf, bufPos, volLabel, -1); 2551 bufPos += CoreResumeKey.LENGTH; 2552 2553 2555 buf[bufPos++] = (byte) (FileAttribute.Volume & 0x00FF); 2556 2557 2559 for (int i = 0; i < 8; i++) 2560 buf[bufPos++] = (byte) 0; 2561 2562 StringBuffer volBuf = new StringBuffer (); 2563 volBuf.append(volLabel); 2564 2565 while (volBuf.length() < 13) 2566 volBuf.append(" "); 2567 2568 if (volBuf.length() > 12) 2569 volBuf.setLength(12); 2570 2571 bufPos = DataPacker.putString(volBuf.toString().toUpperCase(), buf, bufPos, true); 2572 2573 2575 dataLen = bufPos - m_smbPkt.getByteOffset(); 2576 outPkt.setByteCount(dataLen); 2577 2578 2580 m_sess.sendResponseSMB(outPkt); 2581 2582 2584 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_SEARCH)) 2585 logger.debug("Volume label for " + conn.toString() + " is " + volLabel); 2586 return; 2587 } 2588 2589 2594 protected final void procSeekFile(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 2595 { 2596 2597 2599 if (m_smbPkt.checkPacketIsValid(4, 0) == false) 2600 { 2601 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 2602 return; 2603 } 2604 2605 2608 int treeId = m_smbPkt.getTreeId(); 2609 TreeConnection conn = m_sess.findConnection(treeId); 2610 2611 if (conn == null) 2612 { 2613 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 2614 return; 2615 } 2616 2617 2619 if (conn.hasReadAccess() == false) 2620 { 2621 2622 2624 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 2625 return; 2626 } 2627 2628 2630 int fid = m_smbPkt.getParameter(0); 2631 int seekMode = m_smbPkt.getParameter(1); 2632 long seekPos = (long) m_smbPkt.getParameterLong(2); 2633 2634 NetworkFile netFile = conn.findFile(fid); 2635 2636 if (netFile == null) 2637 { 2638 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidHandle, SMBStatus.ErrDos); 2639 return; 2640 } 2641 2642 2644 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 2645 logger.debug("File Seek [" + netFile.getFileId() + "] : Mode = " + seekMode + ", Pos = " + seekPos); 2646 2647 2649 byte[] buf = outPkt.getBuffer(); 2650 long pos = 0; 2651 2652 try 2653 { 2654 2655 2657 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 2658 2659 2661 pos = disk.seekFile(m_sess, conn, netFile, seekPos, seekMode); 2662 } 2663 catch (InvalidDeviceInterfaceException ex) 2664 { 2665 2666 2668 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 2669 return; 2670 } 2671 catch (java.io.IOException ex) 2672 { 2673 2674 2676 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 2677 logger.debug("File Seek Error [" + netFile.getFileId() + "] : " + ex.toString()); 2678 2679 2681 m_sess.sendErrorResponseSMB(SMBStatus.HRDReadFault, SMBStatus.ErrHrd); 2682 return; 2683 } 2684 2685 2687 outPkt.setParameterCount(2); 2688 outPkt.setParameterLong(0, (int) (pos & 0x0FFFFFFFFL)); 2689 outPkt.setByteCount(0); 2690 2691 2693 m_sess.sendResponseSMB(outPkt); 2694 } 2695 2696 2701 2702 protected void procSessionSetup(SMBSrvPacket outPkt) throws SMBSrvException, IOException , 2703 TooManyConnectionsException 2704 { 2705 2706 2708 outPkt.setParameterCount(3); 2709 outPkt.setParameter(0, 0); 2710 outPkt.setParameter(1, 0); 2711 outPkt.setParameter(2, 8192); 2712 outPkt.setByteCount(0); 2713 2714 outPkt.setTreeId(0); 2715 outPkt.setUserId(0); 2716 2717 2719 int pos = outPkt.getByteOffset(); 2720 byte[] buf = outPkt.getBuffer(); 2721 2722 pos = DataPacker.putString("Java", buf, pos, true); 2723 pos = DataPacker.putString("JLAN Server " + m_sess.getServer().isVersion(), buf, pos, true); 2724 pos = DataPacker.putString(m_sess.getServer().getConfiguration().getDomainName(), buf, pos, true); 2725 2726 outPkt.setByteCount(pos - outPkt.getByteOffset()); 2727 2728 2730 m_sess.sendResponseSMB(outPkt); 2731 2732 2734 m_sess.setState(SMBSrvSessionState.SMBSESSION); 2735 } 2736 2737 2744 protected void procSetFileAttributes(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 2745 { 2746 2747 2749 if (m_smbPkt.checkPacketIsValid(8, 0) == false) 2750 { 2751 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 2752 return; 2753 } 2754 2755 2758 int treeId = m_smbPkt.getTreeId(); 2759 TreeConnection conn = m_sess.findConnection(treeId); 2760 2761 if (conn == null) 2762 { 2763 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 2764 return; 2765 } 2766 2767 2769 if (conn.hasWriteAccess() == false) 2770 { 2771 2772 2774 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 2775 return; 2776 } 2777 2778 2780 int dataPos = m_smbPkt.getByteOffset(); 2781 int dataLen = m_smbPkt.getByteCount(); 2782 byte[] buf = m_smbPkt.getBuffer(); 2783 2784 2786 String fileName = DataPacker.getDataString(DataType.ASCII, buf, dataPos, dataLen, m_smbPkt.isUnicode()); 2787 if (fileName == null) 2788 { 2789 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 2790 return; 2791 } 2792 2793 2795 int fattr = m_smbPkt.getParameter(0); 2796 int setFlags = FileInfo.SetAttributes; 2797 2798 FileInfo finfo = new FileInfo(fileName, 0, fattr); 2799 2800 int fdate = m_smbPkt.getParameter(1); 2801 int ftime = m_smbPkt.getParameter(2); 2802 2803 if (fdate != 0 && ftime != 0) 2804 { 2805 finfo.setModifyDateTime(new SMBDate(fdate, ftime).getTime()); 2806 setFlags += FileInfo.SetModifyDate; 2807 } 2808 2809 2811 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 2812 logger.debug("Set File Attributes [" + treeId + "] name=" + fileName + ", attr=0x" 2813 + Integer.toHexString(fattr) + ", fdate=" + fdate + ", ftime=" + ftime); 2814 2815 2817 try 2818 { 2819 2820 2822 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 2823 2824 2826 finfo.setFileInformationFlags(setFlags); 2827 disk.setFileInformation(m_sess, conn, fileName, finfo); 2828 } 2829 catch (InvalidDeviceInterfaceException ex) 2830 { 2831 2832 2834 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 2835 return; 2836 } 2837 catch (java.io.IOException ex) 2838 { 2839 } 2840 2841 2843 outPkt.setParameterCount(0); 2844 outPkt.setByteCount(0); 2845 2846 2848 m_sess.sendResponseSMB(outPkt); 2849 } 2850 2851 2858 protected void procSetFileInformation(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 2859 { 2860 2861 2863 if (m_smbPkt.checkPacketIsValid(7, 0) == false) 2864 { 2865 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 2866 return; 2867 } 2868 2869 2872 int treeId = m_smbPkt.getTreeId(); 2873 TreeConnection conn = m_sess.findConnection(treeId); 2874 2875 if (conn == null) 2876 { 2877 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 2878 return; 2879 } 2880 2881 2883 if (conn.hasWriteAccess() == false) 2884 { 2885 2886 2888 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 2889 return; 2890 } 2891 2892 2894 int fid = m_smbPkt.getParameter(0); 2895 NetworkFile netFile = conn.findFile(fid); 2896 2897 if (netFile == null) 2898 { 2899 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidHandle, SMBStatus.ErrDos); 2900 return; 2901 } 2902 2903 2905 int setFlags = 0; 2906 FileInfo finfo = new FileInfo(netFile.getName(), 0, 0); 2907 2908 int fdate = m_smbPkt.getParameter(1); 2909 int ftime = m_smbPkt.getParameter(2); 2910 2911 if (fdate != 0 && ftime != 0) 2912 { 2913 finfo.setCreationDateTime(new SMBDate(fdate, ftime).getTime()); 2914 setFlags += FileInfo.SetCreationDate; 2915 } 2916 2917 2919 fdate = m_smbPkt.getParameter(3); 2920 ftime = m_smbPkt.getParameter(4); 2921 2922 if (fdate != 0 && ftime != 0) 2923 { 2924 finfo.setAccessDateTime(new SMBDate(fdate, ftime).getTime()); 2925 setFlags += FileInfo.SetAccessDate; 2926 } 2927 2928 2930 fdate = m_smbPkt.getParameter(5); 2931 ftime = m_smbPkt.getParameter(6); 2932 2933 if (fdate != 0 && ftime != 0) 2934 { 2935 finfo.setModifyDateTime(new SMBDate(fdate, ftime).getTime()); 2936 setFlags += FileInfo.SetModifyDate; 2937 } 2938 2939 2941 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILE)) 2942 logger.debug("Set File Information 2 [" + netFile.getFileId() + "] " + finfo.toString()); 2943 2944 2946 try 2947 { 2948 2949 2951 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 2952 2953 2955 finfo.setFileInformationFlags(setFlags); 2956 disk.setFileInformation(m_sess, conn, netFile.getFullName(), finfo); 2957 } 2958 catch (InvalidDeviceInterfaceException ex) 2959 { 2960 2961 2963 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 2964 return; 2965 } 2966 catch (java.io.IOException ex) 2967 { 2968 } 2969 2970 2972 outPkt.setParameterCount(0); 2973 outPkt.setByteCount(0); 2974 2975 2977 m_sess.sendResponseSMB(outPkt); 2978 } 2979 2980 2988 2989 protected void procTreeConnect(SMBSrvPacket outPkt) throws SMBSrvException, TooManyConnectionsException, 2990 java.io.IOException 2991 { 2992 2993 2995 if (m_smbPkt.checkPacketIsValid(0, 4) == false) 2996 { 2997 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 2998 return; 2999 } 3000 3001 3003 int dataPos = m_smbPkt.getByteOffset(); 3004 int dataLen = m_smbPkt.getByteCount(); 3005 byte[] buf = m_smbPkt.getBuffer(); 3006 3007 3009 boolean isUni = m_smbPkt.isUnicode(); 3010 String uncPath = DataPacker.getDataString(DataType.ASCII, buf, dataPos, dataLen, isUni); 3011 if (uncPath == null) 3012 { 3013 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 3014 return; 3015 } 3016 3017 3019 if (isUni) 3020 { 3021 dataPos = DataPacker.wordAlign(dataPos + 1) + (uncPath.length() * 2) + 2; 3022 dataLen -= (uncPath.length() * 2) + 2; 3023 } 3024 else 3025 { 3026 dataPos += uncPath.length() + 2; 3027 dataLen -= uncPath.length() + 2; 3028 } 3029 3030 String pwd = DataPacker.getDataString(DataType.ASCII, buf, dataPos, dataLen, isUni); 3031 if (pwd == null) 3032 { 3033 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 3034 return; 3035 } 3036 3037 3039 if (isUni) 3040 { 3041 dataPos = DataPacker.wordAlign(dataPos + 1) + (pwd.length() * 2) + 2; 3042 dataLen -= (pwd.length() * 2) + 2; 3043 } 3044 else 3045 { 3046 dataPos += pwd.length() + 2; 3047 dataLen -= pwd.length() + 2; 3048 } 3049 3050 String service = DataPacker.getDataString(DataType.ASCII, buf, dataPos, dataLen, isUni); 3051 if (service == null) 3052 { 3053 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 3054 return; 3055 } 3056 3057 3059 int servType = ShareType.ServiceAsType(service); 3060 if (servType == ShareType.UNKNOWN) 3061 { 3062 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 3063 return; 3064 } 3065 3066 3068 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_TREE)) 3069 logger.debug("Tree connect - " + uncPath + ", " + service); 3070 3071 3073 PCShare share = null; 3074 3075 try 3076 { 3077 share = new PCShare(uncPath); 3078 } 3079 catch (InvalidUNCPathException ex) 3080 { 3081 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 3082 return; 3083 } 3084 3085 3087 if (servType == ShareType.NAMEDPIPE && share.getShareName().compareTo("IPC$") == 0) 3088 servType = ShareType.ADMINPIPE; 3089 3090 3092 SharedDevice shareDev = null; 3093 3094 try 3095 { 3096 3097 3099 shareDev = m_sess.getSMBServer().findShare(share.getNodeName(), share.getShareName(), servType, 3100 getSession(), true); 3101 } 3102 catch (InvalidUserException ex) 3103 { 3104 3105 3107 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 3108 return; 3109 } 3110 catch (Exception ex) 3111 { 3112 3113 3115 m_sess.sendErrorResponseSMB(SMBStatus.SRVInvalidNetworkName, SMBStatus.ErrSrv); 3116 return; 3117 } 3118 3119 3121 if (shareDev == null || shareDev.getType() != servType) 3122 { 3123 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 3124 return; 3125 } 3126 3127 3129 int treeId = m_sess.addConnection(shareDev); 3130 3131 3134 SrvAuthenticator auth = getSession().getSMBServer().getAuthenticator(); 3135 int filePerm = FileAccess.Writeable; 3136 3137 if (auth != null) 3138 { 3139 3140 3142 filePerm = auth.authenticateShareConnect(m_sess.getClientInformation(), shareDev, pwd, m_sess); 3143 if (filePerm < 0) 3144 { 3145 3146 3148 m_sess.sendErrorResponseSMB(SMBStatus.SRVNoAccessRights, SMBStatus.ErrSrv); 3149 return; 3150 } 3151 } 3152 3153 3155 TreeConnection tree = m_sess.findConnection(treeId); 3156 tree.setPermission(filePerm); 3157 3158 3160 outPkt.setParameterCount(2); 3161 3162 outPkt.setParameter(0, buf.length - RFCNetBIOSProtocol.HEADER_LEN); 3163 outPkt.setParameter(1, treeId); 3164 outPkt.setByteCount(0); 3165 3166 3168 outPkt.setAndXCommand(0xFF); 3169 m_sess.sendResponseSMB(outPkt); 3170 3171 3173 if (tree.getInterface() != null) 3174 tree.getInterface().treeOpened(m_sess, tree); 3175 } 3176 3177 3184 protected void procTreeDisconnect(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 3185 { 3186 3187 3189 if (m_smbPkt.checkPacketIsValid(0, 0) == false) 3190 { 3191 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 3192 return; 3193 } 3194 3195 3198 int treeId = m_smbPkt.getTreeId(); 3199 TreeConnection conn = m_sess.findConnection(treeId); 3200 3201 if (conn == null) 3202 { 3203 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 3204 return; 3205 } 3206 3207 3209 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_TREE)) 3210 logger.debug("Tree disconnect - " + treeId + ", " + conn.toString()); 3211 3212 3214 m_sess.removeConnection(treeId); 3215 3216 3218 outPkt.setParameterCount(0); 3219 outPkt.setByteCount(0); 3220 3221 m_sess.sendResponseSMB(outPkt); 3222 3223 3225 if (conn.getInterface() != null) 3226 conn.getInterface().treeClosed(m_sess, conn); 3227 } 3228 3229 3236 protected void procUnLockFile(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 3237 { 3238 3239 3241 if (m_smbPkt.checkPacketIsValid(5, 0) == false) 3242 { 3243 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 3244 return; 3245 } 3246 3247 3250 int treeId = m_smbPkt.getTreeId(); 3251 TreeConnection conn = m_sess.findConnection(treeId); 3252 3253 if (conn == null) 3254 { 3255 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 3256 return; 3257 } 3258 3259 3261 if (conn.hasReadAccess() == false) 3262 { 3263 3264 3266 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 3267 return; 3268 } 3269 3270 3272 int fid = m_smbPkt.getParameter(0); 3273 long lockcnt = m_smbPkt.getParameterLong(1); 3274 long lockoff = m_smbPkt.getParameterLong(3); 3275 3276 NetworkFile netFile = conn.findFile(fid); 3277 3278 if (netFile == null) 3279 { 3280 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidHandle, SMBStatus.ErrDos); 3281 return; 3282 } 3283 3284 3286 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILEIO)) 3287 logger.debug("File UnLock [" + netFile.getFileId() + "] : Offset=" + lockoff + " ,Count=" + lockcnt); 3288 3289 3293 outPkt.setParameterCount(0); 3294 outPkt.setByteCount(0); 3295 3296 3298 m_sess.sendResponseSMB(outPkt); 3299 } 3300 3301 3308 protected final void procUnsupported(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 3309 { 3310 3311 3313 m_sess.sendErrorResponseSMB(SMBStatus.SRVNotSupported, SMBStatus.ErrSrv); 3314 } 3315 3316 3323 protected void procWriteFile(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 3324 { 3325 3326 3328 if (m_smbPkt.checkPacketIsValid(5, 0) == false) 3329 { 3330 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 3331 return; 3332 } 3333 3334 3337 int treeId = m_smbPkt.getTreeId(); 3338 TreeConnection conn = m_sess.findConnection(treeId); 3339 3340 if (conn == null) 3341 { 3342 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 3343 return; 3344 } 3345 3346 3348 if (conn.hasWriteAccess() == false) 3349 { 3350 3351 3353 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 3354 return; 3355 } 3356 3357 3359 int fid = m_smbPkt.getParameter(0); 3360 int wrtcnt = m_smbPkt.getParameter(1); 3361 long wrtoff = (m_smbPkt.getParameter(2) + (m_smbPkt.getParameter(3) << 16)) & 0xFFFFFFFFL; 3362 3363 NetworkFile netFile = conn.findFile(fid); 3364 3365 if (netFile == null) 3366 { 3367 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidHandle, SMBStatus.ErrDos); 3368 return; 3369 } 3370 3371 3373 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILEIO)) 3374 logger.debug("File Write [" + netFile.getFileId() + "] : Size=" + wrtcnt + " ,Pos=" + wrtoff); 3375 3376 3378 byte[] buf = m_smbPkt.getBuffer(); 3379 int pos = m_smbPkt.getByteOffset(); 3380 int wrtlen = 0; 3381 3382 3384 if (buf[pos] != DataType.DataBlock) 3385 { 3386 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 3387 return; 3388 } 3389 3390 try 3391 { 3392 3393 3395 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 3396 3397 3399 pos += 3; 3400 3401 3404 if (wrtcnt == 0) 3405 { 3406 3407 3409 disk.truncateFile(m_sess, conn, netFile, wrtoff); 3410 } 3411 else 3412 { 3413 3414 3416 wrtlen = disk.writeFile(m_sess, conn, netFile, buf, pos, wrtcnt, wrtoff); 3417 } 3418 } 3419 catch (InvalidDeviceInterfaceException ex) 3420 { 3421 3422 3424 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 3425 return; 3426 } 3427 catch (java.io.IOException ex) 3428 { 3429 3430 3432 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILEIO)) 3433 logger.debug("File Write Error [" + netFile.getFileId() + "] : " + ex.toString()); 3434 3435 3437 m_sess.sendErrorResponseSMB(SMBStatus.HRDWriteFault, SMBStatus.ErrHrd); 3438 return; 3439 } 3440 3441 3443 outPkt.setParameterCount(1); 3444 outPkt.setParameter(0, wrtlen); 3445 outPkt.setByteCount(0); 3446 3447 3449 m_sess.sendResponseSMB(outPkt); 3450 } 3451 3452 3459 protected void procWriteAndCloseFile(SMBSrvPacket outPkt) throws java.io.IOException , SMBSrvException 3460 { 3461 3462 3464 if (m_smbPkt.checkPacketIsValid(6, 0) == false) 3465 { 3466 m_sess.sendErrorResponseSMB(SMBStatus.SRVUnrecognizedCommand, SMBStatus.ErrSrv); 3467 return; 3468 } 3469 3470 3473 int treeId = m_smbPkt.getTreeId(); 3474 TreeConnection conn = m_sess.findConnection(treeId); 3475 3476 if (conn == null) 3477 { 3478 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidDrive, SMBStatus.ErrDos); 3479 return; 3480 } 3481 3482 3484 if (conn.hasWriteAccess() == false) 3485 { 3486 3487 3489 m_sess.sendErrorResponseSMB(SMBStatus.DOSAccessDenied, SMBStatus.ErrDos); 3490 return; 3491 } 3492 3493 3495 int fid = m_smbPkt.getParameter(0); 3496 int wrtcnt = m_smbPkt.getParameter(1); 3497 int wrtoff = m_smbPkt.getParameterLong(2); 3498 3499 NetworkFile netFile = conn.findFile(fid); 3500 3501 if (netFile == null) 3502 { 3503 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidHandle, SMBStatus.ErrDos); 3504 return; 3505 } 3506 3507 3509 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILEIO)) 3510 logger.debug("File Write And Close [" + netFile.getFileId() + "] : Size=" + wrtcnt + " ,Pos=" + wrtoff); 3511 3512 3514 byte[] buf = m_smbPkt.getBuffer(); 3515 int pos = m_smbPkt.getByteOffset() + 1; int wrtlen = 0; 3517 3518 try 3519 { 3520 3521 3523 DiskInterface disk = (DiskInterface) conn.getSharedDevice().getInterface(); 3524 3525 3527 wrtlen = disk.writeFile(m_sess, conn, netFile, buf, pos, wrtcnt, wrtoff); 3528 3529 3533 if (disk != null) 3534 disk.closeFile(m_sess, conn, netFile); 3535 3536 3538 netFile.setClosed(true); 3539 } 3540 catch (InvalidDeviceInterfaceException ex) 3541 { 3542 3543 3545 m_sess.sendErrorResponseSMB(SMBStatus.DOSInvalidData, SMBStatus.ErrDos); 3546 return; 3547 } 3548 catch (java.io.IOException ex) 3549 { 3550 3551 3553 if (logger.isDebugEnabled() && m_sess.hasDebug(SMBSrvSession.DBG_FILEIO)) 3554 logger.debug("File Write Error [" + netFile.getFileId() + "] : " + ex.toString()); 3555 3556 3558 m_sess.sendErrorResponseSMB(SMBStatus.HRDWriteFault, SMBStatus.ErrHrd); 3559 return; 3560 } 3561 3562 3564 outPkt.setParameterCount(1); 3565 outPkt.setParameter(0, wrtlen); 3566 outPkt.setByteCount(0); 3567 3568 outPkt.setError(0, 0); 3569 3570 3572 m_sess.sendResponseSMB(outPkt); 3573 } 3574 3575 3580 public boolean runProtocol() throws java.io.IOException , SMBSrvException, TooManyConnectionsException 3581 { 3582 3583 3585 if (m_smbPkt == null) 3586 m_smbPkt = new SMBSrvPacket(m_sess.getBuffer()); 3587 3588 3590 boolean handledOK = true; 3591 SMBSrvPacket outPkt = m_smbPkt; 3592 3593 switch (m_smbPkt.getCommand()) 3594 { 3595 3596 3598 case PacketType.SessionSetupAndX: 3599 procSessionSetup(outPkt); 3600 break; 3601 3602 3604 case PacketType.TreeConnect: 3605 procTreeConnect(outPkt); 3606 break; 3607 3608 3610 case PacketType.TreeDisconnect: 3611 procTreeDisconnect(outPkt); 3612 break; 3613 3614 3616 case PacketType.Search: 3617 procSearch(outPkt); 3618 break; 3619 3620 3622 case PacketType.DiskInformation: 3623 procDiskAttributes(outPkt); 3624 break; 3625 3626 3628 case PacketType.GetFileAttributes: 3629 procGetFileAttributes(outPkt); 3630 break; 3631 3632 3634 case PacketType.SetFileAttributes: 3635 procSetFileAttributes(outPkt); 3636 break; 3637 3638 3640 case PacketType.QueryInformation2: 3641 procGetFileInformation(outPkt); 3642 break; 3643 3644 3646 case PacketType.SetInformation2: 3647 procSetFileInformation(outPkt); 3648 break; 3649 3650 3652 case PacketType.OpenFile: 3653 procOpenFile(outPkt); 3654 break; 3655 3656 3658 case PacketType.ReadFile: 3659 procReadFile(outPkt); 3660 break; 3661 3662 3664 case PacketType.SeekFile: 3665 procSeekFile(outPkt); 3666 break; 3667 3668 3670 case PacketType.CloseFile: 3671 procCloseFile(outPkt); 3672 break; 3673 3674 3676 case PacketType.CreateFile: 3677 case PacketType.CreateNew: 3678 procCreateFile(outPkt); 3679 break; 3680 3681 3683 case PacketType.WriteFile: 3684 procWriteFile(outPkt); 3685 break; 3686 3687 3689 case PacketType.WriteAndClose: 3690 procWriteAndCloseFile(outPkt); 3691 break; 3692 3693 3695 case PacketType.FlushFile: 3696 procFlushFile(outPkt); 3697 break; 3698 3699 3701 case PacketType.RenameFile: 3702 procRenameFile(outPkt); 3703 break; 3704 3705 3707 case PacketType.DeleteFile: 3708 procDeleteFile(outPkt); 3709 break; 3710 3711 3713 case PacketType.CreateDirectory: 3714 procCreateDirectory(outPkt); 3715 break; 3716 3717 3719 case PacketType.DeleteDirectory: 3720 procDeleteDirectory(outPkt); 3721 break; 3722 3723 3725 case PacketType.CheckDirectory: 3726 procCheckDirectory(outPkt); 3727 break; 3728 3729 3731 case PacketType.IOCtl: 3732 procUnsupported(outPkt); 3733 break; 3734 3735 3737 case PacketType.Echo: 3738 procEcho(outPkt); 3739 break; 3740 3741 3743 case PacketType.ProcessExit: 3744 procProcessExit(outPkt); 3745 break; 3746 3747 3749 case PacketType.CreateTemporary: 3750 procCreateTemporaryFile(outPkt); 3751 break; 3752 3753 3755 case PacketType.LockFile: 3756 procLockFile(outPkt); 3757 break; 3758 3759 3761 case PacketType.UnLockFile: 3762 procUnLockFile(outPkt); 3763 break; 3764 3765 3767 default: 3768 3769 3771 handledOK = false; 3772 break; 3773 } 3774 3775 3777 return handledOK; 3778 } 3779} | Popular Tags |