dart-lang / sdk

The Dart SDK, including the VM, JS and Wasm compilers, analysis, core libraries, and more.
https://dart.dev
BSD 3-Clause "New" or "Revised" License
10.23k stars 1.57k forks source link

Problems mapping coverage tokens back to code ranges #33359

Closed DanTup closed 6 years ago

DanTup commented 6 years ago

@a-siva @devoncarew

I'm trying to map coverage tokens back to code ranges using the "next token" position as discussed yesterday. I tried this, but it seems like there are "holes" in the coverage data interpreting it this way.

Consider this file (this is from the Stocks example in the Flutter repo, reformatted with dartfmt before I started testing):

// Copyright 2015 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

import 'package:flutter/material.dart';

import 'stock_data.dart';
import 'stock_row.dart';

class StockList extends StatelessWidget {
  const StockList(
      {Key key, this.stocks, this.onOpen, this.onShow, this.onAction})
      : super(key: key);

  final List<Stock> stocks;
  final StockRowActionCallback onOpen;
  final StockRowActionCallback onShow;
  final StockRowActionCallback onAction;

  @override
  Widget build(BuildContext context) {
    return new ListView.builder(
      key: const ValueKey<String>('stock-list'),
      itemExtent: StockRow.kHeight,
      itemCount: stocks.length,
      itemBuilder: (BuildContext context, int index) {
        return new StockRow(
            stock: stocks[index],
            onPressed: onOpen,
            onDoubleTap: onShow,
            onLongPressed: onAction);
      },
    );
  }
}

Here's how it looks in my IDE with line numbers (note: the grey // StockRow and // ListView.builder towards the end of IDE decorations and not part of the code):

screen shot 2018-06-06 at 8 30 25 am

When I look at the coverage data and try to map it back to lines as discussed, here's what I get:

Token 309 seems to go from 11 to 11
Token 586 seems to go from 21 to 21
Token 631 seems to go from 22 to 22
Token 751 seems to go from 25 to 25
Token 758 seems to go from 25 to 25
Token 785 seems to go from 26 to 26
Token 840 seems to go from 27 to 27
Token 869 seems to go from 28 to 28
Token 875 seems to go from 28 to 28
Token 907 seems to go from 29 to 29
Token 940 seems to go from 30 to 30
Token 975 seems to go from 31 to 31

The numbers generally look good (line 11 is the constructor, line 21 starts the build method) but for some reason there's no coverage for line 23 or 24, but looking at the Code I would've expected it).

Here's the coverage report:

{
    "jsonrpc": "2.0",
    "result": {
        "type": "SourceReport",
        "ranges": [
            {
                "scriptIndex": 0,
                "startPos": 309,
                "endPos": 414,
                "compiled": true,
                "coverage": {
                    "hits": [
                        309
                    ],
                    "misses": []
                }
            },
            {
                "scriptIndex": 0,
                "startPos": 586,
                "endPos": 1004,
                "compiled": true,
                "coverage": {
                    "hits": [
                        586,
                        631,
                        751,
                        758
                    ],
                    "misses": []
                }
            },
            {
                "scriptIndex": 0,
                "startPos": 785,
                "endPos": 993,
                "compiled": true,
                "coverage": {
                    "hits": [
                        785,
                        840,
                        869,
                        875,
                        907,
                        940,
                        975
                    ],
                    "misses": []
                }
            }
        ],
        "scripts": [
            {
                "type": "@Script",
                "fixedId": true,
                "id": "libraries\/@510268448\/scripts\/file%3A%2F%2F%2FUsers%2Fdantup%2FDev%2FGoogle%2Fflutter%2Fexamples%2Fstocks%2Flib%2Fstock_list.dart\/163d403a270",
                "uri": "file:\/\/\/Users\/dantup\/Dev\/Google\/flutter\/examples\/stocks\/lib\/stock_list.dart",
                "_kind": "kernel"
            }
        ]
    },
    "id": "16125"
}

Am I doing this correctly? Or should I only look at the tokens in that small range of code (eg. the union of the token numbers in hits and misses when picking the "next token"?

DanTup commented 6 years ago

Or should I only look at the tokens in that small range of code (eg. the union of the token numbers in hits and misses when picking the "next token"?

Thinking about this more, I think this makes sense if only a subset of the tokens are "executable". I should be running up to the next "executable" token. I'll give it a shot and update back here with more testing...

DanTup commented 6 years ago

Seems to work great; unexecuted lines now seem to match what I'd expect (whitespace/comment lines are already excluded by me).

screen shot 2018-06-06 at 8 54 29 am

So closing this - I think I may have another issue, but I'll dig further and open a more case with specifics if I think I need help.