📄 tds.java
字号:
{
flagData[i] = comm.getByte ();
bytesRead++;
}
boolean nullable = (flagData[2] & 0x01) > 0;
boolean writeable = (flagData[2] & 0x08) > 0;
boolean autoIncrement = (flagData[2] & 0x10) > 0;
// Get the type of column
byte columnType = comm.getByte();
bytesRead++;
if (columnType == SYBTEXT
|| columnType == SYBIMAGE)
{
int i;
int tmpByte;
// XXX Need to find out what these next 4 bytes are
// Could they be the column size?
comm.skip(4);
bytesRead += 4;
int tableNameLen = comm.getTdsShort();
bytesRead += 2;
String tableName = encoder.getString(comm.getBytes(tableNameLen));
bytesRead += tableNameLen;
sizeOfColumn = 2<<31 - 1;
}
else if (columnType == SYBDECIMAL
|| columnType == SYBNUMERIC)
{
int tmp;
sizeOfColumn = comm.getByte();
bytesRead++;
precision = comm.getByte(); // Total number of digits
bytesRead++;
scale = comm.getByte(); // # of digits after the decimal point
bytesRead++;
}
else if (isFixedSizeColumn(columnType))
{
sizeOfColumn = lookupColumnSize(columnType);
}
else
{
sizeOfColumn = ((int) comm.getByte() & 0xff);
bytesRead++;
}
numColumns++;
if (scale != -1)
{
columns.setScale(numColumns, scale);
}
if (precision != -1)
{
columns.setPrecision(numColumns, precision);
}
columns.setType(numColumns, columnType);
columns.setDisplaySize(numColumns, sizeOfColumn);
columns.setNullable(numColumns, (nullable
? ResultSetMetaData.columnNullable
: ResultSetMetaData.columnNoNulls));
columns.setAutoIncrement(numColumns, autoIncrement);
columns.setReadOnly(numColumns, !writeable);
}
// Don't know what the rest is except that the
int skipLen = totalLen - bytesRead;
if (skipLen != 0)
{
throw new TdsException(
"skipping " + skipLen + " bytes");
}
return new PacketColumnInfoResult(columns);
} // processColumnInfo
private PacketTabNameResult processTabName()
throws java.io.IOException, com.internetcds.jdbc.tds.TdsException
{
int totalLen = comm.getTdsShort();
// RMK 2000-06-11. Not sure why the original code is bothering
// to extract the bytes with such meticulous care if it isn't
// going to use the extracted strings for creating the returned
// object. At any rate, this approach doesn't work under TDS 7.0,
// because (1) the name length is a short, not a byte under 7.0,
// and (2) the name string is nameLen wide characters for 7.0,
// not 8-bit characters. So I'm commenting the wasted effort
// and replacing it with a simple call to TdsComm.skip().
//int bytesRead = 0;
//int nameLen = 0;
//String tabName = null;
//while(bytesRead < totalLen)
//{
// nameLen = comm.getByte();
// bytesRead++;
// tabName = new String(comm.getBytes(nameLen));
// bytesRead += nameLen;
//}
comm.skip(totalLen);
return new PacketTabNameResult();
} // processTabName()
/**
* Process an end subpacket.
* <p>
* This routine assumes that the TDS_END_TOKEN byte has already
* been read.
*
* @return
*
* @exception com.internetcds.jdbc.tds.TdsException
*
* @exception java.io.IOException
* Thrown if some sort of error occured reading bytes from the network.
*/
private PacketEndTokenResult processEndToken(
byte packetType)
throws com.internetcds.jdbc.tds.TdsException, java.io.IOException
{
byte status = comm.getByte();
comm.skip(3);
int rowCount = comm.getTdsInt();
if (packetType==TdsDefinitions.TDS_DONEINPROC)
{
throw new TdsException("Internal error. TDS_DONEINPROC "
+ " is no longer considered an end token");
}
PacketEndTokenResult result = new PacketEndTokenResult(packetType,
status, rowCount);
moreResults = result.moreResults();
// XXX If we executed something that returns multiple result
// sets then we don't want to clear the query in progress flag.
// See the CancelController class for details.
cancelController.finishQuery(result.wasCanceled(),
result.moreResults());
// XXX Problem handling cancels that were sent after the server
// send the endToken packet
return result;
}
private PacketDoneInProcResult processDoneInProc(
byte packetType)
throws TdsException, java.io.IOException
{
byte status = comm.getByte();
comm.skip(3);
int rowCount = comm.getTdsInt();
PacketDoneInProcResult result = new PacketDoneInProcResult(packetType,
status,
rowCount);
if (!result.moreResults())
{
throw new TdsException("What? No more results with a DONEINPROC!");
}
if (result.moreResults() && peek()==TdsDefinitions.TDS_DONEINPROC)
{
result = (PacketDoneInProcResult)processSubPacket();
}
while (result.moreResults() &&
(peek()==TdsDefinitions.TDS_PROCID
|| peek()==TdsDefinitions.TDS_RET_STAT_TOKEN))
{
if (peek()==TDS_PROCID)
{
PacketResult tmp = processSubPacket();
}
else if (peek()==TDS_RET_STAT_TOKEN)
{
PacketRetStatResult tmp = (PacketRetStatResult)processSubPacket();
result.setRetStat(tmp.getRetStat());
}
}
// XXX If we executed something that returns multiple result
// sets then we don't want to clear the query in progress flag.
// See the CancelController class for details.
cancelController.finishQuery(result.wasCanceled(),
result.moreResults());
return result;
}
/**
* Process a subpacket reply
* <p>
* <b>Note-</b> All subpackets must be processed through here.
* This is the only routine has the proper locking to support
* the cancel method in the Statement class.
* <br>
*
* @return packet subtype the was processed.
*/
PacketResult processSubPacket()
throws TdsUnknownPacketSubType,
java.io.IOException,
com.internetcds.jdbc.tds.TdsException
{
return processSubPacket(null);
}
/**
* Process a subpacket reply
* <p>
* <b>Note-</b> All subpackets must be processed through here. Only this
* routine has the proper locking to support the cancel method in the
* Statement class.
* <br>
*
*
* @return packet subtype the was processed.
*/
synchronized PacketResult processSubPacket(Context context)
throws TdsUnknownPacketSubType,
java.io.IOException,
com.internetcds.jdbc.tds.TdsException
{
// NOTE!!! Before adding anything to this list you must
// consider the ramifications to the the handling of cancels
// as implemented by the CancelController class.
//
// The CancelController class might implicitly assume it can call
// processSubPacket() whenever it is looking for a cancel
// acknowledgment. It assumes that any results of the call
// can be discarded.
PacketResult result = null;
moreResults = false;
byte packetSubType = comm.getByte();
Logger.println("processSubPacket: " +
Integer.toHexString(packetSubType & 0xFF) + " " +
"moreResults: " + moreResults());
switch(packetSubType)
{
case TDS_ENV_CHG_TOKEN:
{
result = processEnvChange();
break;
}
case TDS_ERR_TOKEN:
case TDS_MSG_TOKEN:
case TDS_MSG50_TOKEN:
{
result = processMsg(packetSubType);
break;
}
case TDS_TEXT_UPD_TOKEN:
{
int len = getSubPacketLength();
comm.skip(len);
result = new PacketResult(TDS_TEXT_UPD_TOKEN);
break;
}
case TDS_LOGIN_ACK_TOKEN:
{
result = processLoginAck();
break;
}
case TDS_RET_STAT_TOKEN:
{
result = processRetStat();
break;
}
case TDS_PROCID:
{
result = processProcId();
break;
}
case TDS_DONEINPROC:
{
result = processDoneInProc(packetSubType);
break;
}
case TDS_DONEPROC:
case TDS_END_TOKEN:
{
result = processEndToken(packetSubType);
moreResults2 = ((PacketEndTokenResult)result).moreResults();
break;
}
case TDS_COL_NAME_TOKEN:
{
result = processColumnNames();
break;
}
case TDS_COL_INFO_TOKEN:
{
result = processColumnInfo();
break;
}
case TDS_UNKNOWN_0xA5:
case TDS_UNKNOWN_0xA7:
case TDS_UNKNOWN_0xA8:
{
// XXX Need to figure out what this packet is
comm.skip(comm.getTdsShort());
result = new PacketUnknown(packetSubType);
break;
}
case TDS_TABNAME:
{
result = processTabName();
break;
}
case TDS_ORDER:
{
int len = comm.getTdsShort();
comm.skip(len);
result = new PacketColumnOrderResult();
break;
}
case TDS_CONTROL:
{
int len = comm.getTdsShort();
comm.skip(len);
// FIXME - I'm just ignoring this
result = new PacketControlResult();
break;
}
case TDS_ROW_TOKEN:
{
result = getRow(context.getColumnInfo());
break;
}
case TDS7_RESULT_TOKEN:
{
result = processTds7Result();
break;
}
default:
{
throw new TdsUnknownPacketSubType(packetSubType);
}
}
return result;
}
/**
* Find out how many bytes a particular SQLServer data type takes.
*
* @param nativeColumnType
*
* @return number of bytes required by the given type
*
* @exception com.internetcds.jdbc.tds.TdsException
* Thrown if the given type either doesn't exist or is a variable
* sized data type.
*/
private int lookupColumnSize(byte nativeColumnType)
throws com.internetcds.jdbc.tds.TdsException
{
switch(nativeColumnType)
{
case SYBINT1:
{
return 1;
}
case SYBINT2:
{
return 2;
}
case SYBINT4:
{
return 4;
}
case SYBREAL:
{
return 4;
}
case SYBFLT8:
{
return 8;
}
case SYBDATETIME:
{
return 8;
}
case SYBDATETIME4:
{
return 8;
}
case SYBBIT:
{
return 1;
}
case SYBMONEY:
{
return 8;
}
case SYBMONEY4:
case SYBSMALLMONEY:
{
return 4;
}
default:
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -