Please start any new threads on our new
site at https://forums.sqlteam.com. We've got lots of great SQL Server
experts to answer whatever question you can come up with.
Author |
Topic |
Glockenspiel
Yak Posting Veteran
50 Posts |
Posted - 2002-06-24 : 17:37:07
|
I'm trying to get some baseline performance metrics on uptime, CPU usage, and io for my SQL Server. Here's what I've started -- just curious if anyone else has some better ideas or may have gone down this path before me. Thanks!SELECT CONVERT(VARCHAR(24),crdate,113) AS time_restart, CONVERT(VARCHAR(24),GETDATE(),113) AS time_now, DATEDIFF(mi,crdate,GETDATE()) AS minutes_since_restart, @@cpu_busy/15000.0 AS minutes_cpu_busy, @@io_busy/15000.0 AS minutes_io_busy, @@idle/15000.0 AS minutes_idle,(@@cpu_busy+@@io_busy+@@idle)/15000.0 AS minutes_since_restart2, @@connections AS connectionsFROM master..sysdatabasesWHERE name = 'tempdb'Sample Results Set:time_restart time_now minutes_since_restart minutes_cpu_busy minutes_io_busy minutes_idle minutes_since_restart2 connections ------------------------ ------------------------ --------------------- -------------------- -------------------- -------------------- ---------------------- ----------- 23 Jun 2002 19:34:21:623 25 Jun 2002 10:15:49:077 2321 182.6625333 10.9890666 2128.1510666 2321.8026666 25961Edited by - Glockenspiel on 06/25/2002 11:15:26 |
|
Page47
Master Smack Fu Yak Hacker
2878 Posts |
Posted - 2002-06-25 : 08:53:13
|
This is more of an abstract answer than I am sure you would like, but....when you begin the task of performance tuning, no matter how basic, it is vital that you have a goal in mind. This query if nifty, and it may very well be what you want, however, since you are asking, I'd bet you are not sure what you want. The query/perfmon/trace/statistics is the easy part, deciding what exactly you want to measure is a bit more difficult . . .<O> |
|
|
Glockenspiel
Yak Posting Veteran
50 Posts |
Posted - 2002-06-25 : 10:31:15
|
quote: This is more of an abstract answer than I am sure you would like, but....when you begin the task of performance tuning, no matter how basic, it is vital that you have a goal in mind.
We're looking for a nice and easy, simple, and somewhat foolproof way to get some baseline data on CPU utilization and up-time (time since last restart). The fewer "moving parts" the better (i.e., we don't want to set up a PerfMon or Profiler to run on this box.) |
|
|
Glockenspiel
Yak Posting Veteran
50 Posts |
Posted - 2002-06-25 : 11:27:02
|
I've updated the prior post; it looks like you have to divide the system statistical functions by 15000.0 to get values in minutes (somebody please explain this one to me). Also, it looks like @@cpu_busy + @@io_busy + @@idle add up correctly this way. This obviates the need to use tempdb's crdate as the start date since the ms since service started can be computed backwards by multiplying by -4 (again, somebody please explain this one to me).Simply:SELECT @@cpu_busy/15000.0 AS minutes_cpu_busy, @@io_busy/15000.0 AS minutes_io_busy, @@idle/15000.0 AS minutes_idle,(@@cpu_busy+@@io_busy+@@idle)/15000.0 AS minutes_since_restart, DATEADD(ms,-4*(@@cpu_busy+@@io_busy+@@idle),GETDATE()) AS computed_startup_timeAnd viola, the numbers and times make sense!!!! |
|
|
Glockenspiel
Yak Posting Veteran
50 Posts |
Posted - 2002-06-25 : 11:39:59
|
OK; newsflash... this seems to be CPU-related. In other words:multiply by -4 if your machine is 8-waymultiply by -8 if your machine is 4-waymultiply by -16 if your machine is 2-waymultiply by -32 if your machine is 1-wayEdited by - Glockenspiel on 06/25/2002 11:45:27 |
|
|
Glockenspiel
Yak Posting Veteran
50 Posts |
Posted - 2002-06-25 : 12:16:10
|
OK; here's a cleaned up version of the code:DECLARE @multiplier TINYINT--Remove comment for the multiplier that suits your # of CPUs--SET @multiplier = 32 -- This is for a 1-way machine --SET @multiplier = 16 -- This is for a 2-way machine --SET @multiplier = 8 -- This is for a 4-way machine --SET @multiplier = 4 -- This is for a 8-way machine SELECT @@cpu_busy / 60000.0 * @multiplier AS minutes_cpu_busy, @@io_busy / 60000.0 * @multiplier AS minutes_io_busy, @@idle / 60000.0 * @multiplier AS minutes_idle, (@@cpu_busy + @@io_busy + @@idle) / 60000.0 * @multiplier AS minutes_since_restart, DATEADD(ms, -1 * @multiplier * (@@cpu_busy + @@io_busy + @@idle), GETDATE()) AS computed_startup_timeEdited by - Glockenspiel on 06/25/2002 12:18:48 |
|
|
Page47
Master Smack Fu Yak Hacker
2878 Posts |
Posted - 2002-06-25 : 12:41:26
|
I like...so should I assume it that the multipler for a three way would be 12?<O>Edited by - Page47 on 06/25/2002 12:42:43 |
|
|
efelito
Constraint Violating Yak Guru
478 Posts |
Posted - 2002-06-25 : 12:42:35
|
From BOL:quote: Returns the time in milliseconds (based on the resolution of the system timer) that the CPU has spent doing work since Microsoft® SQL Server™ was last started
The number you are dividing by depends on your processor speed. So to get the cpu minutes busy and have it work across all of your servers you would need to do something like this...declare @mspertick intselect @mspertick = convert(int, @@timeticks / 1000.0) SELECT ((@@cpu_busy*@mspertick)/1000.0)/60 AS minutes_cpu_busyJeff BanschbachConsultant, MCDBAEdited by - efelito on 06/25/2002 12:43:59 |
|
|
Glockenspiel
Yak Posting Veteran
50 Posts |
Posted - 2002-06-25 : 12:58:11
|
I think BOL is bollocks -- their timeticks method (as per the previous poster's query) yields consistently illogical results. The only thing that seems to work is using a multiplier that is purely number-of-CPUs based and not clock-speed-based. I've tested this on a variety of machines with a variety of clock speeds and numbers of CPUs and I seem to be getting consistently correct and logical results.Edited by - Glockenspiel on 06/25/2002 12:59:07 |
|
|
graz
Chief SQLTeam Crack Dealer
4149 Posts |
Posted - 2002-06-25 : 13:12:03
|
Here's a little script I wrote to show an ISP who'se using most of their resources over a given range of time:declare @Seconds intset nocount onIf @Seconds IS NULL Set @Seconds = 10 CREATE TABLE [#sysprocess] ( [spid] [smallint] NOT NULL , [blocked] [smallint] NOT NULL , [cpu] [int] NOT NULL , [physical_io] [bigint] NOT NULL , [memusage] [int] NOT NULL , [open_tran] [smallint] NOT NULL , [status] [nchar] (30) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL , [cmd] [nchar] (16) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL , [loginame] [nchar] (128) COLLATE SQL_Latin1_General_CP1_CI_AS NOT NULL , [tStamp] [datetime] NULL CONSTRAINT [DF__hold_sysp__tStam__5AAF56EE] DEFAULT (getdate())) Declare @i intset @i = 0While @i <= @Secondsbegin insert #sysprocess (spid, blocked, cpu, physical_io, memusage, open_tran, status, cmd, loginame ) select spid, blocked, cpu, physical_io, memusage, open_tran, status, cmd, loginame from master..sysprocesses set @i = @i + 1 waitfor delay '00:00:01'enddeclare @total_ms numeric(8,2)declare @StartTime datetime, @StopTime datetimedeclare @msg varchar(1000)-- by loginameSelect @StartTime = min(tstamp) , @StopTime = max(tstamp) , @total_ms = datediff(ms, min(tstamp), max(tstamp))from dbo.hold_sysprocessPrint 'Started at: ' + convert(varchar, @StartTime) Print ' 'Print 'Duration (ms): ' + convert(varchar, @total_ms)Print ' '--Print 'Results by loginame:'Print '---------- CPU Users -----------'Print ' 'select top 10 left(loginame, 20) as loginame, sum(CPU) as [CPU (ms)], convert(numeric(5,0), convert( numeric(8,2), sum(CPU)) / @total_ms * 100 ) as CPU_Pct, sum(IO) as IO, Sum(Mem) as Mem_pages, Sum(Mem) * 8 as Mem_KBFrom (select spid, loginame, CPU = max_cpu - min_cpu, IO = max_io - min_io, Mem = max_memusagefrom (select spid, loginame, min(cpu) as min_cpu, max(cpu) as max_cpu, min(physical_io) as min_io, Max(physical_io) as max_io, max(memusage) as max_memusagefrom #sysprocessgroup by spid, loginame) as a ) as bgroup by loginameOrder by 2 desc, 5 descPrint ' 'Print '---------- Memory Users -----------'Print ' 'select top 10 left(loginame, 20) as loginame, sum(CPU) as [CPU (ms)], convert(numeric(5,0), convert( numeric(8,2), sum(CPU)) / @total_ms * 100 ) as CPU_Pct, sum(IO) as IO, Sum(Mem) as Mem_pages, Sum(Mem) * 8 as Mem_KBFrom (select spid, loginame, CPU = max_cpu - min_cpu, IO = max_io - min_io, Mem = max_memusagefrom (select spid, loginame, min(cpu) as min_cpu, max(cpu) as max_cpu, min(physical_io) as min_io, Max(physical_io) as max_io, max(memusage) as max_memusagefrom #sysprocessgroup by spid, loginame) as a ) as bgroup by loginameOrder by 5 desc, 2 descPrint ' 'Print '---------- IO Users -----------'Print ' 'select top 10 left(loginame, 20) as loginame, sum(CPU) as [CPU (ms)], convert(numeric(5,0), convert( numeric(8,2), sum(CPU)) / @total_ms * 100 ) as CPU_Pct, sum(IO) as IO, Sum(Mem) as Mem_pages, Sum(Mem) * 8 as Mem_KBFrom (select spid, loginame, CPU = max_cpu - min_cpu, IO = max_io - min_io, Mem = max_memusagefrom (select spid, loginame, min(cpu) as min_cpu, max(cpu) as max_cpu, min(physical_io) as min_io, Max(physical_io) as max_io, max(memusage) as max_memusagefrom #sysprocessgroup by spid, loginame) as a ) as bgroup by loginamehaving Sum(IO) <> 0Order by 4 desc, 2 descdrop table #sysprocessset nocount off It's not especially pretty but it seems to work.===============================================Creating tomorrow's legacy systems today.One crisis at a time. |
|
|
MichaelP
Jedi Yak
2489 Posts |
Posted - 2002-06-25 : 13:40:37
|
Page47, as soon as you have 3 CPU's running in a box, let me know.I'm pretty sure you can only have them in multiples of 22468Michael--------------------<Yoda>Use the Search page you must. |
|
|
Page47
Master Smack Fu Yak Hacker
2878 Posts |
Posted - 2002-06-25 : 13:52:40
|
Will you buy me a if I am right?Come on over and we'll crack the case on this mofo....It's a three way, it reports 3 processors, perfmon lets me choose from three processors, it was speced for three processors.....EDIT:xp_cmdshell 'set number_of_processors'output--------------------------------------NUMBER_OF_PROCESSORS=3(1 row(s) affected)<O>Edited by - Page47 on 06/25/2002 14:03:15 |
|
|
setbasedisthetruepath
Used SQL Salesman
992 Posts |
Posted - 2002-06-25 : 14:05:58
|
quote: Page47, as soon as you have 3 CPU's running in a box, let me know.I'm pretty sure you can only have them in multiples of 22468
To the best of my knowledge, you could only have them in powers of 2, as in 2,4,8,16 ...But, Page's proof is in ...Jonathan Boott, MCDBA |
|
|
MichaelP
Jedi Yak
2489 Posts |
Posted - 2002-06-25 : 14:59:14
|
Page, you actually have a 3-way box? Wow!Who makes it? What model is it? I've GOT to see thing!The only way I can think of getting 3 cpu's in one PC is with those Industrial PC's that use single board computers, but even still I don't think you can have all three working in concert.Michael--------------------<Yoda>Use the Search page you must. |
|
|
Page47
Master Smack Fu Yak Hacker
2878 Posts |
Posted - 2002-06-25 : 15:20:51
|
Hold onto your shorts . . . its made by a little, unknown company called Compaq . . . a 6500 I believe . . .In all fairness, I've never seen one either. But sure enuff, here I am at a client site with a three-way 6500 production database server....sql seems to use all three, with the affinity_mask set to 0.<O> |
|
|
Glockenspiel
Yak Posting Veteran
50 Posts |
Posted - 2002-06-25 : 17:28:40
|
quote: Here's a little script I wrote to show an ISP who'se using most of their resources over a given range of time:
Thanks graz, I'll give this a whirl. |
|
|
ThreePea
Yak Posting Veteran
83 Posts |
Posted - 2002-12-27 : 11:42:05
|
quote: DECLARE @multiplier TINYINT--Remove comment for the multiplier that suits your # of CPUs--SET @multiplier = 32 -- This is for a 1-way machine --SET @multiplier = 16 -- This is for a 2-way machine --SET @multiplier = 8 -- This is for a 4-way machine --SET @multiplier = 4 -- This is for a 8-way machine
Ok. This sounds great, but something was fishy when I attempted to use this code for some performance metrics on our development machine. So I wrote the following script which should return the correct multiplier:DECLARE @uptime_seconds1 INTDECLARE @uptime_seconds2 INTSELECT @uptime_seconds1 = DATEDIFF(s, crdate, GETDATE())FROM master..sysdatabases WHERE NAME = 'tempdb'SET @uptime_seconds2 = (@@CPU_BUSY + @@IO_BUSY + @@IDLE) / 1000SELECT (@uptime_seconds1 * 1.0) / @uptime_seconds2 AS 'Multiplier' When I run this on our 1-processor development machine I get 32, right on the money. However, when I run this on our 4-proc production machine, I get 18.8! No matter how many different methods I use to calculate the multiplier on production I keep getting 18.8. Now that I know what the multiplier is I can use it, but it doesn't make any sense. Any ideas?==================================================Tolerance is the last virtue of an immoral society. -- G.K. Chesterton |
|
|
ValterBorges
Master Smack Fu Yak Hacker
1429 Posts |
Posted - 2002-12-27 : 19:26:48
|
quote: DECLARE @multiplier TINYINT --Remove comment for the multiplier that suits your # of CPUs --SET @multiplier = 32 -- This is for a 1-way machine --SET @multiplier = 16 -- This is for a 2-way machine --SET @multiplier = 8 -- This is for a 4-way machine --SET @multiplier = 4 -- This is for a 8-way machine
Looks to me like the multiplier is 32.0/#Processors.You could useEXEC master.dbo.xp_msver 'ProcessorCount' to find out the number of Processors.Edited by - ValterBorges on 12/27/2002 19:33:56 |
|
|
robvolk
Most Valuable Yak
15732 Posts |
Posted - 2003-01-01 : 13:49:05
|
Just out of curiosity, have you tried using sp_monitor? |
|
|
ThreePea
Yak Posting Veteran
83 Posts |
Posted - 2003-01-02 : 12:23:57
|
quote: EXEC master.dbo.xp_msver 'ProcessorCount'to find out the number of Processors.
ValterBorges, thanks for the tip on xp_msver, now my script is generic. quote: Just out of curiosity, have you tried using sp_monitor?
Rob, I just tried using sp_monitor. I get an error:Server: Msg 8115, Level 16, State 2, Procedure sp_monitor, Line 94Arithmetic overflow error converting expression to data type int.Unfortunately, I don't have the time to debug sp_monitor right now and see what is overflowing. However, my actual question is that I have one machine that does not seem to adhere to the (32 / #processors) formula for the correct multiplier. The script I posted a couple posts back in this thread uses reverse calculations to show the true multiplier on the machine where it is run.When I run this on my 1-processor machine, it returns 32. Check. When I run it on my 2-processor machine, it returns 16. Check. However, when I run it on my 4-processor machine (which is our production server), I get 17.2. Huh? A few days ago the same script was returning 18.8. I'm just trying to see if anyone knows why this machine doesn't follow the formula. Obviously, I am missing something (actually, many things, but we won't go into that here ).Thanks.==================================================Tolerance is the last virtue of an immoral society. -- G.K. Chesterton |
|
|
|
|
|
|
|