Login or Sign Up to become a member!
LessThanDot Sit Logo

LessThanDot

Data Management

Less Than Dot is a community of passionate IT professionals and enthusiasts dedicated to sharing technical knowledge, experience, and assistance. Inside you will find reference materials, interesting technical discussions, and expert tips and commentary. Once you register for an account you will have immediate access to the forums and all past articles and commentaries.

LTD Social Sitings

Lessthandot twitter Lessthandot Linkedin Lessthandot friendfeed Lessthandot facebook Lessthandot rss

Note: Watch for social icons on posts by your favorite authors to follow their postings on these and other social sites.

Your profile

    Search

    XML Feeds

    Google Ads

    « SQL Saturday in Chicago - Schedule is up!Use Filters in SSMS to only see the things that are of interest to you »
    comments

    If you are using snapshots be aware that running sp_helpdb reports wrong files. Let's take a look by running some code

    First create a test database

    1. use master
    2. go
    3.  
    4. CREATE DATABASE [test] ON  PRIMARY
    5. ( NAME = N'test', FILENAME = N'C:\test.mdf'  )
    6.  LOG ON
    7. ( NAME = N'test_log', FILENAME = N'C:\test_log.LDF' )
    8.  
    9. GO

    Now let's create a table and populate it with some data

    1. USE test
    2. go
    3.  
    4.  
    5. create table TestTable (id int not null,somecol char(100) default 'a')
    6. go
    7.  
    8. insert TestTable(id)
    9. select row_number() over (order by s1.id)
    10. from sysobjects s1
    11. cross join sysobjects s2
    12.  
    13. go

    Now create the snapshot database

    1. use master
    2. go
    3.  
    4.    
    5.     CREATE DATABASE TestSnapshot ON  
    6. ( NAME = N'test', FILENAME = N'C:\testss.mdf' )
    7.   AS SNAPSHOT of Test;
    8. GO

    Now run a count for that table against the test database and against the snapshot

    1. select COUNT(*) from TestSnapshot..TestTable
    2. select COUNT(*) from Test..TestTable
    Output
    --------------
    3025
    3025

    As you can see the count is the same

    Now run sp_helpdb and look at the sizes, we will come back to this output later

    1. sp_helpdb 'Test'
    Output
    ---------------------------------------------------------------
    test		1	C:\test.mdf		PRIMARY	2304 KB
    test_log	2	C:\test_log.LDF	        NULL	1792 KB

    Let's add some more data to our table

    1. use Test
    2. go
    3.  
    4. declare @id int =(select MAX(id)
    5.                     from  Test..TestTable)
    6.  
    7. insert Test..TestTable(id)
    8. select row_number() over (order by s1.id) + @id
    9. from sysobjects s1
    10. cross join sysobjects s2
    11. cross join sysobjects s3

    Now if we run the count we will see that the count for the table in the Test database has increased (as expected)

    1. select COUNT(*) from TestSnapshot..TestTable
    2. select COUNT(*) from Test..TestTable
    Output
    -------------
    3025
    169400

    Okay now it is time to run sp_helpdb again

    1. sp_helpdb 'Test'
    Output
    ---------------------------------------------------------------
    test		1	C:\test.mdf		PRIMARY	20736 KB
    test_log	2	C:\test_log.LDF	        NULL	69760 KB
    1. sp_helpdb 'TestSnapshot'
    Output
    ---------------------------------------------------------------
    test		1	C:\test.mdf		PRIMARY	2304 KB
    test_log	2	C:\test_log.LDF	        NULL	1792 KB

    Do you see that? When you run sp_helpdb against the snapshot now it reports what we had originally for the Test database when we ran sp_helpdb before adding rows to the table

    Now run this query

    1. select db_name(dbid) as DB_Name,name,filename,size * 8 from master..sysaltfiles
    2. where dbid in (db_id('Test'),db_id('TestSnapshot'))
    Output
    ---------------------------------------------------------------
    DB_Name			name		filename	size
    test			test		C:\test.mdf	20736
    test			test_log	C:\test_log.LDF	69760
    TestSnapshot	        test		C:\testss.mdf	2304

    As you can see, this reports the correct files and sizes for both Test and the snapshot.

    So where is the problem? The problem is in the sysfiles table, it has the wrong filename

    Run these two queries to verify that

    1. select size * 8 as Size,filename from Test..sysfiles
    2. select size * 8 as Size,filename from TestSnapshot..sysfiles
    Output
    ----------------------------
    Size        filename
    20736       C:\test.mdf
    69760       C:\test_log.LDF
    
    Size        filename
    2304        C:\test.mdf
    1792        C:\test_log.LDF

    sp_helpdb actually calls the sys.sp_helpfile proc to get the size and file name
    run this and you will see that it is the second result set of sp_helpdb

    1. exec Test.sys.sp_helpfile
    2. exec TestSnapshot.sys.sp_helpfile

    Inside the sys.sp_helpfile proc you will find the following code

    1. select  name,  fileid, filename,  
    2.  filegroup = filegroup_name(groupid),  
    3.  'size' = convert(nvarchar(15), convert (bigint, size) * 8) + N' KB',  
    4.  'maxsize' = (case maxsize when -1 then N'Unlimited'  
    5.    else  
    6.    convert(nvarchar(15), convert (bigint, maxsize) * 8) + N' KB' end),  
    7.  'growth' = (case status & 0x100000 when 0x100000 then  
    8.   convert(nvarchar(15), growth) + N'%'  
    9.   else  
    10.   convert(nvarchar(15), convert (bigint, growth) * 8) + N' KB' end),  
    11.  'usage' = (case status & 0x40 when 0x40 then 'log only' else 'data only' end)  
    12.  from sysfiles

    As you can see it uses the sysfiles table

    If you want to see what the code for sp_helpdb and sys.sp_helpfile looks like execute the following

    1. exec sp_helptext 'sp_helpdb'
    2. exec sp_helptext 'sys.sp_helpfile'

    So what do you think, is this a bug?




    *** Remember, if you have a SQL related question, try our Microsoft SQL Server Programming forum or our Microsoft SQL Server Admin forum

    About the Author

    User bio imageDenis has been working with SQL Server since version 6.5. Although he worked as an ASP/JSP/ColdFusion developer before the dot com bust, he has been working exclusively as a database developer/architect since 2002. In addition to English, Denis is also fluent in Croatian and Dutch, but he can curse in many other languages and dialects (just ask the SQL optimizer) He lives in Princeton, NJ with his wife and three kids.
    Social SitingsTwitterFacebookLinkedInHomePageFlickrLTD RSS Feed
    1117 views
    Instapaper

    No feedback yet

    Leave a comment


    Your email address will not be revealed on this site.

    Your URL will be displayed.
    (Line breaks become <br />)
    (Name, email & website)
    (Allow users to contact you through a message form (your email will not be revealed.)