IO_STALL คำถามและความเข้าใจ


9

ฉันกำลังรวบรวม IO_STALLS จาก sys.dm_io_virtual_file_stats ทุก ๆ 5 นาทีจากนั้นทำเดลต้าเพื่อดูว่าไฟล์ใดบ้างที่ได้รับผลกระทบมากที่สุดจาก IO

ในระยะเวลาหนึ่ง 5 นาทีฉันจะได้เดลต้าของ 5826331 ms ซึ่งเป็น 97 นาที

ฉันสับสนเล็กน้อยในเรื่องนี้นี่เป็นการบอกว่าการผ่าตัดเริ่มต้นแล้ว 97 นาทีที่แล้วเพิ่งจะเสร็จที่จุดนั้นและด้วยเหตุนี้จึงบันทึกเวลารอคอยหรือไม่

ขอบคุณ

เพิ่มรหัสตามที่ร้องขอ:

/*

USE [SysDBA]
GO
*/
/****** Object:  Table [dbo].[DISKIOPS]    Script Date: 04/07/2013 11:40:15 ******/
/*
DROP TABLE [dbo].[DISKIOPS]
GO
*/
--Create the table
/****** Object:  Table [dbo].[DISKIOPS]    Script Date: 04/07/2013 11:40:15 ******/
/*
SET ANSI_NULLS ON
GO

SET QUOTED_IDENTIFIER ON
GO

SET ANSI_PADDING ON
GO

CREATE TABLE [dbo].[DISKIOPS](
    [IO_STALL] [bigint] NULL,
    [IO_STALL_READ_MS] [bigint] NULL,
    [IO_STALL_WRITE_MS] [bigint] NULL,
    [NUM_OF_READS] [bigint] NULL,
    [NUM_OF_WRITES] [bigint] NULL,
    [SIZE_ON_DISK_MB] [bigint] NULL,
    [DBNAME] [varchar](max) NULL,
    [NAME] [varchar](max) NULL,
    [FILE_ID] [int] NULL,
    [DB_FILE_TYPE] [varchar](max) NULL,
    [DISK] [varchar](max) NULL,
    [FILE_LOCATION] [varchar](max) NULL,
    [TIMESTAMP] [datetime] NULL
) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]

GO

SET ANSI_PADDING OFF
GO

*/

--Capture IO information from DMV and query to find deltas over time.
/*
USE [SysDBA]
GO

INSERT INTO [dbo].[DISKIOPS]
           ([IO_STALL]
           ,[IO_STALL_READ_MS]
           ,[IO_STALL_WRITE_MS]
           ,[NUM_OF_READS]
           ,[NUM_OF_WRITES]
           ,[SIZE_ON_DISK_MB]
           ,[DBNAME]
           ,[NAME]
           ,[FILE_ID]
           ,[DB_FILE_TYPE]
           ,[DISK]
           ,[FILE_LOCATION]
           ,[TIMESTAMP])
SELECT a.io_stall, a.io_stall_read_ms, a.io_stall_write_ms, a.num_of_reads, 
a.num_of_writes, 
--a.sample_ms, a.num_of_bytes_read, a.num_of_bytes_written,
( ( a.size_on_disk_bytes / 1024 ) / 1024.0 ) AS size_on_disk_mb, 
db_name(a.database_id) AS dbname, 
b.name, a.file_id, 
db_file_type = CASE 
                   WHEN a.file_id = 2 THEN 'Log' 
                   ELSE 'Data' 
                   END, 
UPPER(SUBSTRING(b.physical_name, 1, 2)) AS disk_location,
b.physical_name AS File_location,
GETDATE() AS Timestamp
FROM sys.dm_io_virtual_file_stats (NULL, NULL) a 
JOIN sys.master_files b ON a.file_id = b.file_id 
AND a.database_id = b.database_id
GO
*/
DECLARE @File_Name VARCHAR(8000),
        @Disk VARCHAR(5)
SET @File_Name = 'DBTEST'
SET @Disk = 'I:'
--Code to pull out deltas between collected IO stats.
;WITH IOPS   ([IO_STALL]
           ,[IO_STALL_READ_MS]
           ,[IO_STALL_WRITE_MS]
           ,[NUM_OF_READS]
           ,[NUM_OF_WRITES]
           ,[SIZE_ON_DISK_MB]
           ,[DBNAME]
           ,[NAME]
           ,[FILE_ID]
           ,[DB_FILE_TYPE]
           ,[DISK]
           ,[FILE_LOCATION]
           ,[TIMESTAMP]
           ,[ROW])
AS
(
SELECT *, ROW_NUMBER() OVER (PARTITION BY FILE_LOCATION ORDER BY TIMESTAMP DESC) AS [ROW]
FROM dbo.DISKIOPS 
)

SELECT MAX([IO2].[IO_STALL] - [IO1].[IO_STALL])
FROM IOPS IO1 JOIN IOPS IO2 ON IO1.ROW = (IO2.ROW+1)
WHERE IO1.NAME = IO2.NAME
AND IO1.Disk = @Disk

1
io_stallด้วยตัวเองไม่ได้มีความหมายมากเกินไป หากใน 10 วินาทีคุณมีการหยุดงาน 1,000 ครั้งต่อ 1 วินาทีคุณจะมีแผงขาย 1000 วินาที นั่นจะเป็นแผงลอย 16+ นาทีใน 10 วินาที คุณต้องเชื่อมโยงสิ่งนี้กับการทำงานของ IO คุณสามารถโพสต์คำถามจริงของคุณในคำถามของคุณ?
Thomas Stringer

สวัสดีฉันได้เพิ่มรหัสฉันมีปัญหาเล็กน้อยในการจัดรูปแบบดังนั้นฉันหวังว่ามันจะโอเค
Tom

คำตอบ:


10

ความคิดเห็นของคำถามถูกวางไว้ด้านล่าง:

io_stallด้วยตัวเองไม่ได้มีความหมายมากเกินไป หากใน 10 วินาทีคุณมีการหยุดงาน 1,000 ครั้งต่อ 1 วินาทีคุณจะมีแผงขาย 1000 วินาที นั่นจะเป็นแผงลอย 16+ นาทีใน 10 วินาที คุณต้องเชื่อมโยงสิ่งนี้กับการปฏิบัติการ IO ...

ด้านบนเป็นตัวอย่างที่ดีในการเห็นตัวเลขที่เกินจริงและดูเกินจริง โดยตัวมันเองio_stallไม่ได้มีความหมายอะไรเลย คุณจำเป็นต้องรู้ขนาดของการดำเนินการ I / O สำหรับแผงลอยสะสมนั้น

แทนที่จะมีสิ่งนี้:

SELECT MAX([IO2].[IO_STALL] - [IO1].[IO_STALL])
FROM IOPS IO1 JOIN IOPS IO2 ON IO1.ROW = (IO2.ROW+1)
...

คุณต้องแบ่งแผงควบคุมโดยการทำงานของ I / O เพื่อรับแผงลอยเฉลี่ยต่อ I / O (หรือต่อการอ่านหรือเขียนหรือสิ่งที่คุณกำลังมองหา) คำแนะนำของฉันคือการปรับเปลี่ยนการค้นหาของคุณเพื่อให้มีลักษณะดังนี้:

SELECT
    MAX(([IO2].[IO_STALL] - [IO1].[IO_STALL]) / (IO2.NUM_OF_READS + IO2.NUM_OF_WRITES - IO1.NUM_OF_READS - IO1.NUM_OF_WRITES))
FROM IOPS IO1 JOIN IOPS IO2 ON IO1.ROW = (IO2.ROW+1)

และจากนั้นคุณต้องมีส่วนคำสั่งเพิ่มเติมเพื่อให้แน่ใจว่าคุณไม่ได้หารด้วยศูนย์:

...
WHERE IO1.NAME = IO2.NAME
and (IO2.NUM_OF_READS + IO2.NUM_OF_WRITES - IO1.NUM_OF_READS - IO1.NUM_OF_WRITES) > 0
AND IO1.Disk = @Disk

สิ่งนี้โดยทั่วไปไม่สามารถคำนวณค่าเฉลี่ยio_stallต่อการดำเนินงานของ I / O ด้วยตัวเองสูงio_stallอาจหมายถึงภาระงานที่สูงขึ้นและไม่จำเป็นต้องเป็นสัญญาณของปัญหา


2
ใช่ฉันเข้าใจแล้วขอบคุณมากหวังว่าข้อผิดพลาดของฉันจะเป็นประโยชน์ต่อผู้อื่น
Tom

2
มันเป็นข้อผิดพลาดทั่วไปไม่เพียง แต่กับสถิติไฟล์เสมือน แต่ยังรอสถิติ ดีใจที่มันช่วย!
Thomas Stringer
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.