text:
package de.danoeh.antennapod.core.storage;

import android.app.Application;
import android.content.Context;
import android.content.SharedPreferences;
import android.database.Cursor;
import android.util.Log;

import androidx.core.util.Consumer;
import androidx.preference.PreferenceManager;
import androidx.test.platform.app.InstrumentationRegistry;

import org.awaitility.Awaitility;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.robolectric.RobolectricTestRunner;

import java.io.File;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Locale;
import java.util.concurrent.Future;
import java.util.concurrent.TimeUnit;

import de.danoeh.antennapod.core.ApplicationCallbacks;
import de.danoeh.antennapod.core.ClientConfig;
import de.danoeh.antennapod.model.feed.Feed;
import de.danoeh.antennapod.model.feed.FeedItem;
import de.danoeh.antennapod.model.feed.FeedMedia;
import de.danoeh.antennapod.core.preferences.PlaybackPreferences;
import de.danoeh.antennapod.core.preferences.UserPreferences;
import de.danoeh.antennapod.core.util.FeedItemUtil;

import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertTrue;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.when;

/**
 * Test class for {@link DBWriter}.
 */
@RunWith(RobolectricTestRunner.class)
public class DbWriterTest {

    private static final String TAG = "DBWriterTest";
    private static final String TEST_FOLDER = "testDBWriter";
    private static final long TIMEOUT = 5L;

    private Context context;

    @Before
    public void setUp() {
        context = InstrumentationRegistry.getInstrumentation().getTargetContext();
        UserPreferences.init(context);
        PlaybackPreferences.init(context);

        Application app = (Application) context;
        ClientConfig.applicationCallbacks = mock(ApplicationCallbacks.class);
        when(ClientConfig.applicationCallbacks.getApplicationInstance()).thenReturn(app);

        // create new database
        PodDBAdapter.init(context);
        PodDBAdapter.deleteDatabase();
        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.close();

        SharedPreferences.Editor prefEdit = PreferenceManager.getDefaultSharedPreferences(
                context.getApplicationContext()).edit();
        prefEdit.putBoolean(UserPreferences.PREF_DELETE_REMOVES_FROM_QUEUE, true).commit();
    }

    @After
    public void tearDown() {
        PodDBAdapter.tearDownTests();
        DBWriter.tearDownTests();

        File testDir = context.getExternalFilesDir(TEST_FOLDER);
        assertNotNull(testDir);
        for (File f : testDir.listFiles()) {
            //noinspection ResultOfMethodCallIgnored
            f.delete();
        }
    }

    @Test
    public void testSetFeedMediaPlaybackInformation() throws Exception {
        final int position = 50;
        final long lastPlayedTime = 1000;
        final int playedDuration = 60;
        final int duration = 100;

        Feed feed = new Feed("url", null, "title");
        List<FeedItem> items = new ArrayList<>();
        feed.setItems(items);
        FeedItem item = new FeedItem(0, "Item", "Item", "url", new Date(), FeedItem.PLAYED, feed);
        items.add(item);
        FeedMedia media = new FeedMedia(0, item, duration, 1, 1, "mime_type",
                "dummy path", "download_url", true, null, 0, 0);
        item.setMedia(media);

        DBWriter.setFeedItem(item).get(TIMEOUT, TimeUnit.SECONDS);

        media.setPosition(position);
        media.setLastPlayedTime(lastPlayedTime);
        media.setPlayedDuration(playedDuration);

        DBWriter.setFeedMediaPlaybackInformation(item.getMedia()).get(TIMEOUT, TimeUnit.SECONDS);

        FeedItem itemFromDb = DBReader.getFeedItem(item.getId());
        FeedMedia mediaFromDb = itemFromDb.getMedia();

        assertEquals(position, mediaFromDb.getPosition());
        assertEquals(lastPlayedTime, mediaFromDb.getLastPlayedTime());
        assertEquals(playedDuration, mediaFromDb.getPlayedDuration());
        assertEquals(duration, mediaFromDb.getDuration());
    }

    @Test
    public void testDeleteFeedMediaOfItemFileExists() throws Exception {
        File dest = new File(context.getExternalFilesDir(TEST_FOLDER), "testFile");

        assertTrue(dest.createNewFile());

        Feed feed = new Feed("url", null, "title");
        List<FeedItem> items = new ArrayList<>();
        feed.setItems(items);
        FeedItem item = new FeedItem(0, "Item", "Item", "url", new Date(), FeedItem.PLAYED, feed);

        FeedMedia media = new FeedMedia(0, item, 1, 1, 1, "mime_type",
                dest.getAbsolutePath(), "download_url", true, null, 0, 0);
        item.setMedia(media);

        items.add(item);

        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.close();
        assertTrue(media.getId() != 0);
        assertTrue(item.getId() != 0);

        DBWriter.deleteFeedMediaOfItem(context, media.getId())
                .get(TIMEOUT, TimeUnit.SECONDS);
        media = DBReader.getFeedMedia(media.getId());
        assertNotNull(media);
        assertFalse(dest.exists());
        assertFalse(media.isDownloaded());
        assertNull(media.getFile_url());
    }

    @Test
    public void testDeleteFeedMediaOfItemRemoveFromQueue() throws Exception {
        assertTrue(UserPreferences.shouldDeleteRemoveFromQueue());

        File dest = new File(context.getExternalFilesDir(TEST_FOLDER), "testFile");

        assertTrue(dest.createNewFile());

        Feed feed = new Feed("url", null, "title");
        List<FeedItem> items = new ArrayList<>();
        feed.setItems(items);
        FeedItem item = new FeedItem(0, "Item", "Item", "url", new Date(), FeedItem.UNPLAYED, feed);

        FeedMedia media = new FeedMedia(0, item, 1, 1, 1, "mime_type",
                dest.getAbsolutePath(), "download_url", true, null, 0, 0);
        item.setMedia(media);

        items.add(item);
        List<FeedItem> queue = new ArrayList<>();
        queue.add(item);

        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.setQueue(queue);
        adapter.close();
        assertTrue(media.getId() != 0);
        assertTrue(item.getId() != 0);
        queue = DBReader.getQueue();
        assertTrue(queue.size() != 0);

        DBWriter.deleteFeedMediaOfItem(context, media.getId());
        Awaitility.await().until(() -> !dest.exists());
        media = DBReader.getFeedMedia(media.getId());
        assertNotNull(media);
        assertFalse(dest.exists());
        assertFalse(media.isDownloaded());
        assertNull(media.getFile_url());
        queue = DBReader.getQueue();
        assertEquals(0, queue.size());
    }

    @Test
    public void testDeleteFeed() throws Exception {
        File destFolder = context.getExternalFilesDir(TEST_FOLDER);
        assertNotNull(destFolder);

        Feed feed = new Feed("url", null, "title");
        feed.setItems(new ArrayList<>());

        List<File> itemFiles = new ArrayList<>();
        // create items with downloaded media files
        for (int i = 0; i < 10; i++) {
            FeedItem item = new FeedItem(0, "Item " + i, "Item" + i, "url", new Date(), FeedItem.PLAYED, feed);
            feed.getItems().add(item);

            File enc = new File(destFolder, "file " + i);
            assertTrue(enc.createNewFile());

            itemFiles.add(enc);
            FeedMedia media = new FeedMedia(0, item, 1, 1, 1, "mime_type",
                    enc.getAbsolutePath(), "download_url", true, null, 0, 0);
            item.setMedia(media);
        }

        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.close();

        assertTrue(feed.getId() != 0);
        for (FeedItem item : feed.getItems()) {
            assertTrue(item.getId() != 0);
            assertTrue(item.getMedia().getId() != 0);
        }

        DBWriter.deleteFeed(context, feed.getId()).get(TIMEOUT, TimeUnit.SECONDS);

        // check if files still exist
        for (File f : itemFiles) {
            assertFalse(f.exists());
        }

        adapter = PodDBAdapter.getInstance();
        adapter.open();
        Cursor c = adapter.getFeedCursor(feed.getId());
        assertEquals(0, c.getCount());
        c.close();
        for (FeedItem item : feed.getItems()) {
            c = adapter.getFeedItemCursor(String.valueOf(item.getId()));
            assertEquals(0, c.getCount());
            c.close();
            c = adapter.getSingleFeedMediaCursor(item.getMedia().getId());
            assertEquals(0, c.getCount());
            c.close();
        }
        adapter.close();
    }

    @Test
    public void testDeleteFeedNoItems() throws Exception {
        File destFolder = context.getExternalFilesDir(TEST_FOLDER);
        assertNotNull(destFolder);

        Feed feed = new Feed("url", null, "title");
        feed.setItems(null);
        feed.setImageUrl("url");

        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.close();

        assertTrue(feed.getId() != 0);

        DBWriter.deleteFeed(context, feed.getId()).get(TIMEOUT, TimeUnit.SECONDS);

        adapter = PodDBAdapter.getInstance();
        adapter.open();
        Cursor c = adapter.getFeedCursor(feed.getId());
        assertEquals(0, c.getCount());
        c.close();
        adapter.close();
    }

    @Test
    public void testDeleteFeedNoFeedMedia() throws Exception {
        File destFolder = context.getExternalFilesDir(TEST_FOLDER);
        assertNotNull(destFolder);

        Feed feed = new Feed("url", null, "title");
        feed.setItems(new ArrayList<>());

        feed.setImageUrl("url");

        // create items
        for (int i = 0; i < 10; i++) {
            FeedItem item = new FeedItem(0, "Item " + i, "Item" + i, "url", new Date(), FeedItem.PLAYED, feed);
            feed.getItems().add(item);

        }

        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.close();

        assertTrue(feed.getId() != 0);
        for (FeedItem item : feed.getItems()) {
            assertTrue(item.getId() != 0);
        }

        DBWriter.deleteFeed(context, feed.getId()).get(TIMEOUT, TimeUnit.SECONDS);

        adapter = PodDBAdapter.getInstance();
        adapter.open();
        Cursor c = adapter.getFeedCursor(feed.getId());
        assertEquals(0, c.getCount());
        c.close();
        for (FeedItem item : feed.getItems()) {
            c = adapter.getFeedItemCursor(String.valueOf(item.getId()));
            assertEquals(0, c.getCount());
            c.close();
        }
        adapter.close();
    }

    @Test
    public void testDeleteFeedWithQueueItems() throws Exception {
        File destFolder = context.getExternalFilesDir(TEST_FOLDER);
        assertNotNull(destFolder);

        Feed feed = new Feed("url", null, "title");
        feed.setItems(new ArrayList<>());

        feed.setImageUrl("url");

        // create items with downloaded media files
        for (int i = 0; i < 10; i++) {
            FeedItem item = new FeedItem(0, "Item " + i, "Item" + i, "url", new Date(), FeedItem.PLAYED, feed);
            feed.getItems().add(item);
            File enc = new File(destFolder, "file " + i);
            FeedMedia media = new FeedMedia(0, item, 1, 1, 1, "mime_type",
                    enc.getAbsolutePath(), "download_url", false, null, 0, 0);
            item.setMedia(media);
        }

        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.close();

        assertTrue(feed.getId() != 0);
        for (FeedItem item : feed.getItems()) {
            assertTrue(item.getId() != 0);
            assertTrue(item.getMedia().getId() != 0);
        }

        List<FeedItem> queue = new ArrayList<>(feed.getItems());
        adapter.open();
        adapter.setQueue(queue);

        Cursor queueCursor = adapter.getQueueIDCursor();
        assertEquals(queue.size(), queueCursor.getCount());
        queueCursor.close();

        adapter.close();
        DBWriter.deleteFeed(context, feed.getId()).get(TIMEOUT, TimeUnit.SECONDS);
        adapter.open();

        Cursor c = adapter.getFeedCursor(feed.getId());
        assertEquals(0, c.getCount());
        c.close();
        for (FeedItem item : feed.getItems()) {
            c = adapter.getFeedItemCursor(String.valueOf(item.getId()));
            assertEquals(0, c.getCount());
            c.close();
            c = adapter.getSingleFeedMediaCursor(item.getMedia().getId());
            assertEquals(0, c.getCount());
            c.close();
        }
        c = adapter.getQueueCursor();
        assertEquals(0, c.getCount());
        c.close();
        adapter.close();
    }

    @Test
    public void testDeleteFeedNoDownloadedFiles() throws Exception {
        File destFolder = context.getExternalFilesDir(TEST_FOLDER);
        assertNotNull(destFolder);

        Feed feed = new Feed("url", null, "title");
        feed.setItems(new ArrayList<>());

        feed.setImageUrl("url");

        // create items with downloaded media files
        for (int i = 0; i < 10; i++) {
            FeedItem item = new FeedItem(0, "Item " + i, "Item" + i, "url", new Date(), FeedItem.PLAYED, feed);
            feed.getItems().add(item);
            File enc = new File(destFolder, "file " + i);
            FeedMedia media = new FeedMedia(0, item, 1, 1, 1, "mime_type",
                    enc.getAbsolutePath(), "download_url", false, null, 0, 0);
            item.setMedia(media);
        }

        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.close();

        assertTrue(feed.getId() != 0);
        for (FeedItem item : feed.getItems()) {
            assertTrue(item.getId() != 0);
            assertTrue(item.getMedia().getId() != 0);
        }

        DBWriter.deleteFeed(context, feed.getId()).get(TIMEOUT, TimeUnit.SECONDS);

        adapter = PodDBAdapter.getInstance();
        adapter.open();
        Cursor c = adapter.getFeedCursor(feed.getId());
        assertEquals(0, c.getCount());
        c.close();
        for (FeedItem item : feed.getItems()) {
            c = adapter.getFeedItemCursor(String.valueOf(item.getId()));
            assertEquals(0, c.getCount());
            c.close();
            c = adapter.getSingleFeedMediaCursor(item.getMedia().getId());
            assertEquals(0, c.getCount());
            c.close();
        }
        adapter.close();
    }

    @Test
    public void testDeleteFeedItems() throws Exception {
        Feed feed = new Feed("url", null, "title");
        feed.setItems(new ArrayList<>());
        feed.setImageUrl("url");

        // create items
        for (int i = 0; i < 10; i++) {
            FeedItem item = new FeedItem(0, "Item " + i, "Item" + i, "url", new Date(), FeedItem.PLAYED, feed);
            feed.getItems().add(item);
        }

        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.close();

        List<FeedItem> itemsToDelete = feed.getItems().subList(0, 2);
        DBWriter.deleteFeedItems(context, itemsToDelete).get(TIMEOUT, TimeUnit.SECONDS);

        adapter = PodDBAdapter.getInstance();
        adapter.open();
        for (int i = 0; i < feed.getItems().size(); i++) {
            FeedItem feedItem = feed.getItems().get(i);
            Cursor c = adapter.getFeedItemCursor(String.valueOf(feedItem.getId()));
            if (i < 2) {
                assertEquals(0, c.getCount());
            } else {
                assertEquals(1, c.getCount());
            }
            c.close();
        }
        adapter.close();
    }

    private FeedMedia playbackHistorySetup(Date playbackCompletionDate) {
        Feed feed = new Feed("url", null, "title");
        feed.setItems(new ArrayList<>());
        FeedItem item = new FeedItem(0, "title", "id", "link", new Date(), FeedItem.PLAYED, feed);
        FeedMedia media = new FeedMedia(0, item, 10, 0, 1, "mime", null,
                "url", false, playbackCompletionDate, 0, 0);
        feed.getItems().add(item);
        item.setMedia(media);
        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.close();
        assertTrue(media.getId() != 0);
        return media;
    }

    @Test
    public void testAddItemToPlaybackHistoryNotPlayedYet() throws Exception {
        FeedMedia media = playbackHistorySetup(null);
        DBWriter.addItemToPlaybackHistory(media).get(TIMEOUT, TimeUnit.SECONDS);
        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        media = DBReader.getFeedMedia(media.getId());
        adapter.close();

        assertNotNull(media);
        assertNotNull(media.getPlaybackCompletionDate());
    }

    @Test
    public void testAddItemToPlaybackHistoryAlreadyPlayed() throws Exception {
        final long oldDate = 0;

        FeedMedia media = playbackHistorySetup(new Date(oldDate));
        DBWriter.addItemToPlaybackHistory(media).get(TIMEOUT, TimeUnit.SECONDS);
        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        media = DBReader.getFeedMedia(media.getId());
        adapter.close();

        assertNotNull(media);
        assertNotNull(media.getPlaybackCompletionDate());
        assertNotEquals(media.getPlaybackCompletionDate().getTime(), oldDate);
    }

    @SuppressWarnings("SameParameterValue")
    private Feed queueTestSetupMultipleItems(final int numItems) throws Exception {
        UserPreferences.setEnqueueLocation(UserPreferences.EnqueueLocation.BACK);
        Feed feed = new Feed("url", null, "title");
        feed.setItems(new ArrayList<>());
        for (int i = 0; i < numItems; i++) {
            FeedItem item = new FeedItem(0, "title " + i, "id " + i, "link " + i, new Date(), FeedItem.PLAYED, feed);
            feed.getItems().add(item);
        }

        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.close();

        for (FeedItem item : feed.getItems()) {
            assertTrue(item.getId() != 0);
        }
        List<Future<?>> futures = new ArrayList<>();
        for (FeedItem item : feed.getItems()) {
            futures.add(DBWriter.addQueueItem(context, item));
        }
        for (Future<?> f : futures) {
            f.get(TIMEOUT, TimeUnit.SECONDS);
        }
        return feed;
    }

    @Test
    public void testAddQueueItemSingleItem() throws Exception {
        Feed feed = new Feed("url", null, "title");
        feed.setItems(new ArrayList<>());
        FeedItem item = new FeedItem(0, "title", "id", "link", new Date(), FeedItem.PLAYED, feed);
        feed.getItems().add(item);

        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.close();

        assertTrue(item.getId() != 0);
        DBWriter.addQueueItem(context, item).get(TIMEOUT, TimeUnit.SECONDS);

        adapter = PodDBAdapter.getInstance();
        adapter.open();
        Cursor cursor = adapter.getQueueIDCursor();
        assertTrue(cursor.moveToFirst());
        assertEquals(item.getId(), cursor.getLong(0));
        cursor.close();
        adapter.close();
    }

    @Test
    public void testAddQueueItemSingleItemAlreadyInQueue() throws Exception {
        Feed feed = new Feed("url", null, "title");
        feed.setItems(new ArrayList<>());
        FeedItem item = new FeedItem(0, "title", "id", "link", new Date(), FeedItem.PLAYED, feed);
        feed.getItems().add(item);

        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.close();

        assertTrue(item.getId() != 0);
        DBWriter.addQueueItem(context, item).get(TIMEOUT, TimeUnit.SECONDS);

        adapter = PodDBAdapter.getInstance();
        adapter.open();
        Cursor cursor = adapter.getQueueIDCursor();
        assertTrue(cursor.moveToFirst());
        assertEquals(item.getId(), cursor.getLong(0));
        cursor.close();
        adapter.close();

        DBWriter.addQueueItem(context, item).get(TIMEOUT, TimeUnit.SECONDS);
        adapter = PodDBAdapter.getInstance();
        adapter.open();
        cursor = adapter.getQueueIDCursor();
        assertTrue(cursor.moveToFirst());
        assertEquals(item.getId(), cursor.getLong(0));
        assertEquals(1, cursor.getCount());
        cursor.close();
        adapter.close();
    }

    @Test
    public void testAddQueueItemMultipleItems() throws Exception {
        final int numItems = 10;

        Feed feed;
        feed = queueTestSetupMultipleItems(numItems);
        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        Cursor cursor = adapter.getQueueIDCursor();
        assertTrue(cursor.moveToFirst());
        assertEquals(numItems, cursor.getCount());
        List<Long> expectedIds;
        expectedIds = FeedItemUtil.getIdList(feed.getItems());
        List<Long> actualIds = new ArrayList<>();
        for (int i = 0; i < numItems; i++) {
            assertTrue(cursor.moveToPosition(i));
            actualIds.add(cursor.getLong(0));
        }
        cursor.close();
        adapter.close();
        assertEquals("Bulk add to queue: result order should be the same as the order given",
                expectedIds, actualIds);
    }

    @Test
    public void testClearQueue() throws Exception {
        final int numItems = 10;

        queueTestSetupMultipleItems(numItems);
        DBWriter.clearQueue().get(TIMEOUT, TimeUnit.SECONDS);
        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        Cursor cursor = adapter.getQueueIDCursor();
        assertFalse(cursor.moveToFirst());
        cursor.close();
        adapter.close();
    }

    @Test
    public void testRemoveQueueItem() throws Exception {
        final int numItems = 10;
        Feed feed = createTestFeed(numItems);

        for (int removeIndex = 0; removeIndex < numItems; removeIndex++) {
            final FeedItem item = feed.getItems().get(removeIndex);
            PodDBAdapter adapter = PodDBAdapter.getInstance();
            adapter.open();
            adapter.setQueue(feed.getItems());
            adapter.close();

            DBWriter.removeQueueItem(context, false, item).get(TIMEOUT, TimeUnit.SECONDS);
            adapter = PodDBAdapter.getInstance();
            adapter.open();
            Cursor queue = adapter.getQueueIDCursor();
            assertEquals(numItems - 1, queue.getCount());
            for (int i = 0; i < queue.getCount(); i++) {
                assertTrue(queue.moveToPosition(i));
                final long queueID = queue.getLong(0);
                assertTrue(queueID != item.getId());  // removed item is no longer in queue
                boolean idFound = false;
                for (FeedItem other : feed.getItems()) { // items that were not removed are still in the queue
                    idFound = idFound | (other.getId() == queueID);
                }
                assertTrue(idFound);
            }
            queue.close();
            adapter.close();
        }
    }

    @Test
    public void testRemoveQueueItemMultipleItems() throws Exception {
        final int numItems = 5;
        final int numInQueue = numItems - 1; // the last one not in queue for boundary condition
        Feed feed = createTestFeed(numItems);

        List<FeedItem> itemsToAdd = feed.getItems().subList(0, numInQueue);
        withPodDB(adapter -> adapter.setQueue(itemsToAdd));

        // Actual tests
        //

        // Use array rather than List to make codes more succinct
        Long[] itemIds = toItemIds(feed.getItems()).toArray(new Long[0]);

        DBWriter.removeQueueItem(context, false,
                itemIds[1], itemIds[3]).get(TIMEOUT, TimeUnit.SECONDS);
        assertQueueByItemIds("Average case - 2 items removed successfully",
                itemIds[0], itemIds[2]);

        DBWriter.removeQueueItem(context, false).get(TIMEOUT, TimeUnit.SECONDS);
        assertQueueByItemIds("Boundary case - no items supplied. queue should see no change",
                itemIds[0], itemIds[2]);

        DBWriter.removeQueueItem(context, false,
                itemIds[0], itemIds[4], -1L).get(TIMEOUT, TimeUnit.SECONDS);
        assertQueueByItemIds("Boundary case - items not in queue ignored",
                itemIds[2]);

        DBWriter.removeQueueItem(context, false,
                itemIds[2], -1L).get(TIMEOUT, TimeUnit.SECONDS);
        assertQueueByItemIds("Boundary case - invalid itemIds ignored"); // the queue is empty

    }

    @Test
    public void testMoveQueueItem() throws Exception {
        final int numItems = 10;
        Feed feed = new Feed("url", null, "title");
        feed.setItems(new ArrayList<>());
        for (int i = 0; i < numItems; i++) {
            FeedItem item = new FeedItem(0, "title " + i, "id " + i, "link " + i,
                    new Date(), FeedItem.PLAYED, feed);
            feed.getItems().add(item);
        }

        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.close();

        for (FeedItem item : feed.getItems()) {
            assertTrue(item.getId() != 0);
        }
        for (int from = 0; from < numItems; from++) {
            for (int to = 0; to < numItems; to++) {
                if (from == to) {
                    continue;
                }
                Log.d(TAG, String.format(Locale.US, "testMoveQueueItem: From=%d, To=%d", from, to));
                final long fromID = feed.getItems().get(from).getId();

                adapter = PodDBAdapter.getInstance();
                adapter.open();
                adapter.setQueue(feed.getItems());
                adapter.close();

                DBWriter.moveQueueItem(from, to, false).get(TIMEOUT, TimeUnit.SECONDS);
                adapter = PodDBAdapter.getInstance();
                adapter.open();
                Cursor queue = adapter.getQueueIDCursor();
                assertEquals(numItems, queue.getCount());
                assertTrue(queue.moveToPosition(from));
                assertNotEquals(fromID, queue.getLong(0));
                assertTrue(queue.moveToPosition(to));
                assertEquals(fromID, queue.getLong(0));

                queue.close();
                adapter.close();
            }
        }
    }

    @Test
    public void testMarkFeedRead() throws Exception {
        final int numItems = 10;
        Feed feed = new Feed("url", null, "title");
        feed.setItems(new ArrayList<>());
        for (int i = 0; i < numItems; i++) {
            FeedItem item = new FeedItem(0, "title " + i, "id " + i, "link " + i,
                    new Date(), FeedItem.UNPLAYED, feed);
            feed.getItems().add(item);
        }

        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.close();

        assertTrue(feed.getId() != 0);
        for (FeedItem item : feed.getItems()) {
            assertTrue(item.getId() != 0);
        }

        DBWriter.markFeedRead(feed.getId()).get(TIMEOUT, TimeUnit.SECONDS);
        List<FeedItem> loadedItems = DBReader.getFeedItemList(feed);
        for (FeedItem item : loadedItems) {
            assertTrue(item.isPlayed());
        }
    }

    @Test
    public void testRemoveAllNewFlags() throws Exception {
        final int numItems = 10;
        Feed feed = new Feed("url", null, "title");
        feed.setItems(new ArrayList<>());
        for (int i = 0; i < numItems; i++) {
            FeedItem item = new FeedItem(0, "title " + i, "id " + i, "link " + i,
                    new Date(), FeedItem.NEW, feed);
            feed.getItems().add(item);
        }

        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.close();

        assertTrue(feed.getId() != 0);
        for (FeedItem item : feed.getItems()) {
            assertTrue(item.getId() != 0);
        }

        DBWriter.removeAllNewFlags().get();
        List<FeedItem> loadedItems = DBReader.getFeedItemList(feed);
        for (FeedItem item : loadedItems) {
            assertFalse(item.isNew());
        }
    }

    @Test
    public void testMarkAllItemsReadSameFeed() throws Exception {
        final int numItems = 10;
        Feed feed = new Feed("url", null, "title");
        feed.setItems(new ArrayList<>());
        for (int i = 0; i < numItems; i++) {
            FeedItem item = new FeedItem(0, "title " + i, "id " + i, "link " + i,
                    new Date(), FeedItem.UNPLAYED, feed);
            feed.getItems().add(item);
        }

        PodDBAdapter adapter = PodDBAdapter.getInstance();
        adapter.open();
        adapter.setCompleteFeed(feed);
        adapter.close();

        assertTrue(feed.getId() != 0);
        for (FeedItem item : feed.getItems()) {
            assertTrue(item.getId() != 0);
        }

        DBWriter.markAllItemsRead().get(TIMEOUT, TimeUnit.SECONDS);
        List<FeedItem> loadedItems = DBReader.getFeedItemList(feed);
        for (FeedItem item : loadedItems) {
            assertTrue(item.isPlayed());
        }
    }

    private static Feed createTestFeed(int numItems) {
        Feed feed = new Feed("url", null, "title");
        feed.setItems(new ArrayList<>());
        for (int i = 0; i < numItems; i++) {
            FeedItem item = new FeedItem(0, "title " + i, "id " + i, "link " + i,
                    new Date(), FeedItem.PLAYED, feed);
            feed.getItems().add(item);
        }

        withPodDB(adapter -> adapter.setCompleteFeed(feed));

        for (FeedItem item : feed.getItems()) {
            assertTrue(item.getId() != 0);
        }
        return feed;
    }

    private static void withPodDB(Consumer<PodDBAdapter> action) {
        PodDBAdapter adapter = PodDBAdapter.getInstance();
        try {
            adapter.open();
            action.accept(adapter);
        } finally {
            adapter.close();
        }
    }

    private static void assertQueueByItemIds(String message, long... itemIdsExpected) {
        List<FeedItem> queue = DBReader.getQueue();
        List<Long> itemIdsActualList = toItemIds(queue);
        List<Long> itemIdsExpectedList = new ArrayList<>(itemIdsExpected.length);
        for (long id : itemIdsExpected) {
            itemIdsExpectedList.add(id);
        }

        assertEquals(message, itemIdsExpectedList, itemIdsActualList);
    }

    private static List<Long> toItemIds(List<FeedItem> items) {
        List<Long> itemIds = new ArrayList<>(items.size());
        for (FeedItem item : items) {
            itemIds.add(item.getId());
        }
        return itemIds;
    }
}


text:
package telas;

import java.awt.Color;
import java.awt.EventQueue;

import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.border.EmptyBorder;

import br.com.conducto.awy.myClient;
import br.com.conductor.sdc.api.v1.invoker.ApiException;
import br.com.conductor.sdc.api.v1.model.Extrato;

import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JTextField;
import javax.swing.ImageIcon;
import javax.swing.JButton;
import java.awt.event.ActionListener;
import java.util.List;
import java.awt.event.ActionEvent;

public class Tela_Consulta extends JFrame {

	/**
	 *
	 */
	private static final long serialVersionUID = 1L;
	private JPanel contentPane;
	private JTextField textField;

	private myClient client;

	   public myClient getClient() {
			return client;
		}

		public void setClient(myClient client) {
			this.client = client;
			System.out.println(client.getCartaoNome());

		}

	public static void main(String[] args) {
		EventQueue.invokeLater(new Runnable() {
			public void run() {
				try {
					Tela_Consulta frame3 = new Tela_Consulta(new myClient());
					frame3.setVisible(true);
				} catch (Exception e) {
					e.printStackTrace();
				}
			}
		});
	}

	/**
	 * Create the frame.
	 */
	public Tela_Consulta(myClient client) {
		setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
		setBounds(100, 100, 450, 130);
		contentPane = new JPanel();
		contentPane.setBorder(new EmptyBorder(5, 5, 5, 5));
		setContentPane(contentPane);
		contentPane.setLayout(null);

		JLabel lblIdClient = new JLabel("Conta: ");
		lblIdClient.setForeground(Color.WHITE);
		lblIdClient.setBounds(12, 42, 70, 15);
		contentPane.add(lblIdClient);

		textField = new JTextField();
		textField.setBounds(100, 40, 315, 19);
		contentPane.add(textField);
		textField.setColumns(10);

		JLabel lblConsulta = new JLabel("Consulta");
		lblConsulta.setForeground(Color.WHITE);
		lblConsulta.setBounds(12, 12, 438, 19);
		contentPane.add(lblConsulta);

		JButton btnNewButton = new JButton("Search");

		btnNewButton.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				Object source = e.getSource();
				if (source instanceof JButton){

					String txt = textField.getText().toString();
					if(txt.equals(client.getContaNome())){
						String itxt = "Cartão: "+client.getContaNome()+"\n"+"Nome: "+client.getCartaoNome();

						 List<Extrato> extratos = null;
						try {
							  extratos = client.getCartaoApi().extratosUsingPOST(client.getConta().getId(), client.getCartao().getId());
							    for(Extrato e1 : extratos){
							    	itxt +=e1;
							    	System.out.println(itxt);
							    }
						} catch (ApiException e1) {
							// TODO Auto-generated catch block
							e1.printStackTrace();
						}
						//txt += " "+extrato;
						JOptionPane.showMessageDialog(null, itxt);
					}
					else{
						JOptionPane.showMessageDialog(null, "Conta não encontrada");
						}
				}
			}
		});
		btnNewButton.setBounds(324, 71, 91, 25);
		contentPane.add(btnNewButton);

		JLabel lblNewLabel = new JLabel("");
		lblNewLabel.setIcon(new ImageIcon("image/teste3.png"));
		lblNewLabel.setBounds(0, -21, 450, 163);
		contentPane.add(lblNewLabel);

	}
}

redpajama_set_name: RedPajamaGithub


text:
package org.jetbrains.plugins.scala.projectHighlighting.downloaded

import org.jetbrains.plugins.scala.HighlightingTests
import org.jetbrains.plugins.scala.projectHighlighting.base.GithubRepositoryWithRevision
import org.junit.experimental.categories.Category

@Category(Array(classOf[HighlightingTests]))
class KorolevProjectHighlightingTest extends GithubSbtAllProjectHighlightingTest {

  //version 0.9.0
  override protected def githubRepositoryWithRevision: GithubRepositoryWithRevision =
    GithubRepositoryWithRevision("fomkin", "korolev", "7d4d41113b574061aedb5a791747b0fa5d122fdf")
}


text:
FROM ubuntu

MAINTAINER Steven E. Pav <shabbychef@gmail.com>

RUN (apt-get update; \
	apt-get install -y make autoconf automake libtool m4 wget curl python3-yaml; \
	mkdir -p /opt/pocketmine; \
	cd /opt/pocketmine && curl -sL http://get.pocketmine.net/ | bash -s - -r -v development)

VOLUME /var/pocketmine
WORKDIR /var/pocketmine

EXPOSE 19132

ENTRYPOINT ["/opt/pocketmine/bin/php5/bin/php"]
CMD ["/opt/pocketmine/PocketMine-MP.phar", "--no-wizard", "--enable-rcon=on","--allow-flight=true","--motd-dockermine","--view-distance=60","--memory-limit=1024M"]

#for vim modeline: (do not edit)
# vim:nu:fdm=marker:fmr=FOLDUP,UNFOLD:cms=#%s:syn=Dockerfile:ft=Dockerfile:fo=croql


text:
<?php

namespace DreadLabs\AppMigration\Lock\NinjaMutex\Tests\Unit\Timeout;

use DreadLabs\AppMigration\Exception\LockingException;
use DreadLabs\AppMigration\Lock\NinjaMutex\Timeout\Waiting;

/**
 * WaitingTest
 *
 * @author Thomas Juhnke <dev@van-tomas.de>
 */
class WaitingTest extends \PHPUnit_Framework_TestCase
{

    public function testItThrowsAnExceptionIfConstructionArgumentIsNotGreaterThanZero()
    {
        $this->setExpectedException(LockingException::class);

        new Waiting(0);
    }

    public function testItThrowsAnExceptionIfConstructionArgumentIsAString()
    {
        $this->setExpectedException(LockingException::class);

        new Waiting('foo');
    }

    public function testItThrowsAnExceptionIfConstructionArgumentIsAnArray()
    {
        $this->setExpectedException(LockingException::class);

        new Waiting(array());
    }

    public function testItThrowsAnExceptionIfConstructionArgumentIsAFloatValueBetweenZeroAndOne()
    {
        $this->setExpectedException(LockingException::class);

        new Waiting(0.5);
    }

    public function testItReturnsTheSameIntegerValueAsGivenOnConstruction()
    {
        $waitingTimeout = new Waiting(2);

        $this->assertSame(2, $waitingTimeout->getValue());
    }

    public function testItReturnsTheFloatValueRoundedToInteger()
    {
        $waitingTimeout = new Waiting(3.14);

        $this->assertSame(3, $waitingTimeout->getValue());
    }
}


text:
================================================================================
DVSFailureCriteria
================================================================================

.. describe:: Property of

    :py:class:`~pyvisdk.do.vmware_uplink_port_teaming_policy.VmwareUplinkPortTeamingPolicy`

.. describe:: See also

    :py:class:`~pyvisdk.do.bool_policy.BoolPolicy`,
    :py:class:`~pyvisdk.do.int_policy.IntPolicy`,
    :py:class:`~pyvisdk.do.string_policy.StringPolicy`

.. describe:: Since

    vSphere API 4.0

.. describe:: Extends

    :py:class:`~pyvisdk.mo.inheritable_policy.InheritablePolicy`

.. class:: pyvisdk.do.dvs_failure_criteria.DVSFailureCriteria

    .. py:attribute:: checkBeacon

        The flag to indicate whether or not to enable this property to enable beacon probing as a method to validate the link status of a physical network adapter.

    .. py:attribute:: checkDuplex

        The flag to indicate whether or not to use the link duplex reported by the driver as link selection criteria.

    .. py:attribute:: checkErrorPercent

        The flag to indicate whether or not to use link error percentage to detect failure.

    .. py:attribute:: checkSpeed

        To use link speed as the criteria,

    .. py:attribute:: fullDuplex

        See checkDuplex

    .. py:attribute:: percentage

        See checkErrorPercent

    .. py:attribute:: speed

        See checkSpeed


text:
class RenameAreaToDatasetIdDatasetEdits < ActiveRecord::Migration[5.0]
  def change
    remove_column :dataset_edits, :area
    add_column :dataset_edits, :dataset_id, :integer, after: :source_id
  end
end


text:
module System.IO.Streams.Logging.Internal.Types
  ( Logger(..)
  , LoggerState(..)
  ) where

------------------------------------------------------------------------------
import           Blaze.ByteString.Builder (Builder)
import           Control.Concurrent.MVar  (MVar)
import           Data.ByteString.Char8    (ByteString)
import           System.IO.Streams        (OutputStream)
------------------------------------------------------------------------------

newtype Logger = Logger { unLogger :: MVar LoggerState }

------------------------------------------------------------------------------
data LoggerState = LoggerState {
      _output      :: {-# UNPACK #-} !(OutputStream Builder)

      -- | Some logger types must be reset for log rotation, e.g. closed and
      -- re-opened again.
    , _resetOutput :: LoggerState -> IO LoggerState

      -- | Error handler to be called to print a secondary message (e.g. to
      -- stderr) if the output stream or reset functions throw an exception.
    , _onError     :: ByteString -> IO ()
    }


text:
package groovy.lang;

import org.codehaus.groovy.runtime.IteratorClosureAdapter;
import org.codehaus.groovy.runtime.RangeInfo;

import java.math.BigInteger;
import java.util.AbstractList;
import java.util.Collection;
import java.util.Iterator;
import java.util.List;

/**
 * Represents a list of Integer objects from a specified int up (or down) to and including
 * a given to.

 *

 * This class is a copy of {@link ObjectRange} optimized for int. If you make any
 * changes to this class, you might consider making parallel changes to {@link ObjectRange}.
 * Instances of this class may be either inclusive aware or non-inclusive aware. See the
 * relevant constructors for creating each type. Inclusive aware IntRange instances are
 * suitable for use with Groovy's range indexing - in particular if the from or to values
 * might be negative. This normally happens underneath the covers but is worth keeping
 * in mind if creating these ranges yourself explicitly.
 *
 * @author James Strachan
 */
public class IntRange extends AbstractList<Integer> implements Range<Integer> {

    /**
     * Iterates through each number in an IntRange.
     */
    private class IntRangeIterator implements Iterator<Integer> {
        /**
         * Counts from 0 up to size - 1.
         */
        private int index;

        /**
         * The number of values in the range.
         */
        private int size = size();

        /**
         * The next value to return.
         */
        private int value = isReverse() ? getTo() : getFrom();

        /**
         * {@inheritDoc}
         */
        public boolean hasNext() {
            return index < size;
        }

        /**
         * {@inheritDoc}
         */
        public Integer next() {
            if (!hasNext()) {
                // TODO instead of returning null, do this: throw new NoSuchElementException();
                return null;
            }
            if (index++ > 0) {
                if (isReverse()) {
                    --value;
                } else {
                    ++value;
                }
            }
            return value;
        }

        /**
         * Not supported.
         *
         * @throws java.lang.UnsupportedOperationException
         *          always
         */
        public void remove() {
            IntRange.this.remove(index);
        }
    }

    /**
     * For non-inclusive aware ranges, the first number in the range; from is always less than or equal to to.
     * For inclusive aware ranges, the from argument supplied to the constructor.
     */
    private int from;

    /**
     * For non-inclusive aware ranges, the last number in the range; to is always greater than or equal to from.
     * For inclusive aware ranges, the from argument supplied to the constructor.
     */
    private int to;

    /**
     * If false, counts up from from to to.  Otherwise, counts down
     * from to to from. Not used for inclusive aware ranges.
     */
    private boolean reverse;

    /**
     * If true, to is included in the range.  Otherwise, the range stops
     * before the to value. Null for non-inclusive aware ranges.
     */
    private Boolean inclusive;

    /**
     * Creates a new non-inclusive IntRange. If from is greater than
     * to, a reverse range is created with from and to swapped.
     *
     * @param from the first number in the range.
     * @param to   the last number in the range.
     * @throws IllegalArgumentException if the range would contain more than {@link Integer#MAX_VALUE} values.
     */
    public IntRange(int from, int to) {
        this.inclusive = null;
        if (from > to) {
            this.from = to;
            this.to = from;
            this.reverse = true;
        } else {
            this.from = from;
            this.to = to;
        }

        // size() in the Collection interface returns an integer, so ranges can have no more than Integer.MAX_VALUE elements
        Long size = 0L + this.to - this.from;
        if (size >= Integer.MAX_VALUE) {
            throw new IllegalArgumentException("A range must have no more than " + Integer.MAX_VALUE + " elements but attempted " + size + " elements");
        }
    }

    /**
     * Creates a new non-inclusive aware IntRange.
     *
     * @param from    the first value in the range.
     * @param to      the last value in the range.
     * @param reverse true if the range should count from
     *                to to from.
     * @throws IllegalArgumentException if from is greater than to.
     */
    protected IntRange(int from, int to, boolean reverse) {
        this.inclusive = null;
        if (from > to) {
            throw new IllegalArgumentException("'from' must be less than or equal to 'to'");
        }

        this.from = from;
        this.to = to;
        this.reverse = reverse;

        // size() in the Collection interface returns an integer, so ranges can have no more than Integer.MAX_VALUE elements
        Long size = 0L + this.to - this.from;
        if (size >= Integer.MAX_VALUE) {
            throw new IllegalArgumentException("A range must have no more than " + Integer.MAX_VALUE + " elements but attempted " + size + " elements");
        }
    }

    /**
     * Creates a new inclusive aware IntRange.
     *
     * @param from    the first value in the range.
     * @param to      the last value in the range.
     * @param inclusive true if the to value is included in the range.
     */
    public IntRange(boolean inclusive, int from, int to) {
        this.from = from;
        this.to = to;
        this.inclusive = inclusive;
    }

    /**
     * A method for determining from and to information when using this IntRange to index an aggregate object of the specified size.
     * Normally only used internally within Groovy but useful if adding range indexing support for your own aggregates.
     *
     * @param size the size of the aggregate being indexed
     * @return the calculated range information (with 1 added to the to value, ready for providing to subList
     */
    public RangeInfo subListBorders(int size) {
        if (inclusive == null) throw new IllegalStateException("Should not call subListBorders on a non-inclusive aware IntRange");
        int tempFrom = from;
        if (tempFrom < 0) {
            tempFrom += size;
        }
        int tempTo = to;
        if (tempTo < 0) {
            tempTo += size;
        }
        if (tempFrom > tempTo) {
            return new RangeInfo(inclusive ? tempTo : tempTo + 1, tempFrom + 1, true);
        }
        return new RangeInfo(tempFrom, inclusive ? tempTo + 1 : tempTo, false);
    }

    /**
     * Determines if this object is equal to another object. Delegates to
     * {@link AbstractList#equals(Object)} if that is anything
     * other than an {@link IntRange}.
     *

     * It is not necessary to override hashCode, as
     * {@link AbstractList#hashCode()} provides a suitable hash code.

     *

     * Note that equals is generally handled by {@link org.codehaus.groovy.runtime.DefaultGroovyMethods#equals(List,List)}
     * instead of this method.
     *
     * @param that the object to compare
     * @return true if the objects are equal
     */
    public boolean equals(Object that) {
        return that instanceof IntRange ? equals((IntRange) that) : super.equals(that);
    }

    /**
     * Compares an {@link IntRange} to another {@link IntRange}.
     *
     * @param that the object to compare for equality
     * @return true if the ranges are equal
     */
    public boolean equals(IntRange that) {
        return that != null && ((this.inclusive == null && this.reverse == that.reverse && this.from == that.from && this.to == that.to)
                || (this.inclusive != null && this.inclusive == that.inclusive && this.from == that.from && this.to == that.to));
    }

    /**
     * {@inheritDoc}
     */
    public Integer getFrom() {
        if (inclusive == null || from <= to) return from;
        return inclusive ? to : to + 1;
    }

    /**
     * {@inheritDoc}
     */
    public Integer getTo() {
        if (inclusive == null) return to;
        if (from <= to) return inclusive ? to : to - 1;
        return from;
    }

    /**
     * Returns the inclusive flag. Null for non-inclusive aware ranges or non-null for inclusive aware ranges.
     */
    public Boolean getInclusive() {
        return inclusive;
    }

    /**
     * Gets the 'from' value as a primitive integer.
     *
     * @return the 'from' value as a primitive integer.
     */
    public int getFromInt() {
        return getFrom();
    }

    /**
     * Gets the 'to' value as a primitive integer.
     *
     * @return the 'to' value as a primitive integer.
     */
    public int getToInt() {
        return getTo();
    }

    /**
     * {@inheritDoc}
     */
    public boolean isReverse() {
        return inclusive == null ? reverse : (from > to);
    }

    public boolean containsWithinBounds(Object o) {
        return contains(o);
    }

    /**
     * {@inheritDoc}
     */
    public Integer get(int index) {
        if (index < 0) {
            throw new IndexOutOfBoundsException("Index: " + index + " should not be negative");
        }
        if (index >= size()) {
            throw new IndexOutOfBoundsException("Index: " + index + " too big for range: " + this);
        }
        return isReverse() ? getTo() - index : index + getFrom();
    }

    /**
     * {@inheritDoc}
     */
    public int size() {
        return getTo() - getFrom() + 1;
    }

    /**
     * {@inheritDoc}
     */
    public Iterator<Integer> iterator() {
        return new IntRangeIterator();
    }

    /**
     * {@inheritDoc}
     */
    public List<Integer> subList(int fromIndex, int toIndex) {
        if (fromIndex < 0) {
            throw new IndexOutOfBoundsException("fromIndex = " + fromIndex);
        }
        if (toIndex > size()) {
            throw new IndexOutOfBoundsException("toIndex = " + toIndex);
        }
        if (fromIndex > toIndex) {
            throw new IllegalArgumentException("fromIndex(" + fromIndex + ") > toIndex(" + toIndex + ")");
        }

        if (fromIndex == toIndex) {
            return new EmptyRange(getFrom());
        }

        return new IntRange(fromIndex + getFrom(), toIndex + getFrom() - 1, isReverse());
    }

    /**
     * {@inheritDoc}
     */
    public String toString() {
        return inclusive != null ? ("" + from + ".." + (inclusive ? "" : "<") + to)
                : (reverse ? "" + to + ".." + from : "" + from + ".." + to);
    }

    /**
     * {@inheritDoc}
     */
    public String inspect() {
        return toString();
    }

    /**
     * {@inheritDoc}
     */
    public boolean contains(Object value) {
        if (value instanceof Integer) {
            return (Integer) value >= getFrom() && (Integer) value <= getTo();
        }
        if (value instanceof BigInteger) {
            BigInteger bigint = (BigInteger) value;
            return bigint.compareTo(BigInteger.valueOf(getFrom())) >= 0 &&
                    bigint.compareTo(BigInteger.valueOf(getTo())) <= 0;
        }
        return false;
    }

    /**
     * {@inheritDoc}
     */
    public boolean containsAll(Collection other) {
        if (other instanceof IntRange) {
            final IntRange range = (IntRange) other;
            return this.getFrom() <= range.getFrom() && range.getTo() <= this.getTo();
        }
        return super.containsAll(other);
    }

    /**
     * {@inheritDoc}
     */
    public void step(int step, Closure closure) {
        if (step == 0) {
            if (!getFrom().equals(getTo())) {
                throw new GroovyRuntimeException("Infinite loop detected due to step size of 0");
            } else {
                return; // from == to and step == 0, nothing to do, so return
            }
        }

        if (isReverse()) {
            step = -step;
        }
        if (step > 0) {
            int value = getFrom();
            while (value <= getTo()) {
                closure.call(Integer.valueOf(value));
                if((0L + value + step) >= Integer.MAX_VALUE) {
                    break;
                }
                value = value + step;
            }
        } else {
            int value = getTo();
            while (value >= getFrom()) {
                closure.call(Integer.valueOf(value));
                if((0L + value + step) <= Integer.MIN_VALUE) {
                    break;
                }
                value = value + step;
            }
        }
    }

    /**
     * {@inheritDoc}
     */
    public List<Integer> step(int step) {
        IteratorClosureAdapter<Integer> adapter = new IteratorClosureAdapter<Integer>(this);
        step(step, adapter);
        return adapter.asList();
    }
}


text:
package com.heaven7.android.data.mediator;

import android.content.res.ColorStateList;
import android.graphics.Bitmap;
import android.graphics.drawable.Drawable;
import android.net.Uri;
import android.support.v4.view.ViewCompat;
import android.support.v7.widget.RecyclerView;
import android.util.TypedValue;
import android.view.View;
import android.widget.Checkable;
import android.widget.ImageView;
import android.widget.ListAdapter;
import android.widget.ListView;
import android.widget.TextView;

import com.heaven7.core.util.ViewHelper;
import com.heaven7.java.data.mediator.Binder;
import com.heaven7.java.data.mediator.DataMediator;
import com.heaven7.java.data.mediator.Property;
import com.heaven7.java.data.mediator.PropertyInterceptor;

/**
 * the binder of android platform. opened in 1.1.0
 * Created by heaven7 on 2017/9/24.
 */
public class AndroidBinder<T> extends Binder<T> {
    /**
     * create binder for target data mediator.
     *
     * @param mMediator the target data mediator.
     */
    public AndroidBinder(DataMediator<T> mMediator) {
        super(mMediator);
    }

    @Override
    public Binder<T> bindVisibility(String property, Object view, boolean forceAsBoolean) {
        if(!(view instanceof View)){
            throw new IllegalArgumentException("must be any child of android.view.View");
        }
        bind(property, new VisibilityBinderCallback<T>((View)view,
                getPropertyInterceptor(), forceAsBoolean));
        return this;
    }

    @Override
    public Binder<T> bindCheckable(String property, Object view){
        if(!(view instanceof Checkable) || !(view instanceof View)){
            throw new IllegalArgumentException("must be Checkable View");
        }
        bind(property, new CheckableBinderCallback<T>((View) view, getPropertyInterceptor()));
        return this;
    }
    @Override
    public Binder<T> bindText(String property, Object tv){
        if(!(tv instanceof TextView)){
            throw new IllegalArgumentException("must be TextView");
        }
        bind(property, new TextBinderCallback<T>((TextView) tv, getPropertyInterceptor()));
        return this;
    }
    @Override
    public Binder<T> bindTextRes(String property, Object tv){
        if(!(tv instanceof TextView)){
            throw new IllegalArgumentException("must be TextView");
        }
        bind(property, new TextResBinderCallback<T>((TextView) tv, getPropertyInterceptor()));
        return this;
    }
    @Override
    public Binder<T> bindTextColor(String property, Object tv){
        if(!(tv instanceof TextView)){
            throw new IllegalArgumentException("must be TextView");
        }
        bind(property, new TextColorBinderCallback<T>((TextView) tv, getPropertyInterceptor()));
        return this;
    }
    @Override
    public Binder<T> bindTextColorRes(String property, Object tv){
        if(!(tv instanceof TextView)){
            throw new IllegalArgumentException("must be TextView");
        }
        bind(property, new TextColorResBinderCallback<T>((TextView) tv, getPropertyInterceptor()));
        return this;
    }
    @Override
    public Binder<T> bindTextSizeRes(String property, Object tv){
        if(!(tv instanceof TextView)){
            throw new IllegalArgumentException("must be TextView");
        }
        bind(property, new TextSizeResBinderCallback<T>((TextView) tv, getPropertyInterceptor()));
        return this;
    }
    @Override
    public Binder<T> bindTextSize(String property, Object tv){
        if(!(tv instanceof TextView)){
            throw new IllegalArgumentException("must be TextView");
        }
        bind(property, new TextSizeDpBinderCallback<T>((TextView) tv, getPropertyInterceptor()));
        return this;
    }
    @Override
    public Binder<T> bindTextSizePx(String property, Object tv) {
        if(!(tv instanceof TextView)){
            throw new IllegalArgumentException("must be TextView");
        }
        bind(property, new TextSizeBinderCallback<T>((TextView) tv, getPropertyInterceptor()));
        return this;
    }

    @Override
    public Binder<T> bindEnable(String property, Object view){
        if(!(view instanceof View)){
            throw new IllegalArgumentException("must be any child of android.view.View");
        }
        bind(property, new EnableBinderCallback<T>((View) view, getPropertyInterceptor()));
        return this;
    }
    @Override
    public Binder<T> bindBackgroundRes(String property, Object view){
        if(!(view instanceof View)){
            throw new IllegalArgumentException("must be any child of android.view.View");
        }
        bind(property, new BackgroundResBinderCallback<T>((View) view, getPropertyInterceptor()));
        return this;
    }
    @Override
    public Binder<T> bindBackground(String property, Object view){
        if(!(view instanceof View)){
            throw new IllegalArgumentException("must be any child of android.view.View");
        }
        bind(property, new BackgroundBinderCallback<T>((View) view, getPropertyInterceptor()));
        return this;
    }
    @Override
    public Binder<T> bindBackgroundColor(String property, Object view){
        if(!(view instanceof View)){
            throw new IllegalArgumentException("must be any child of android.view.View");
        }
        bind(property, new BackgroundColorBinderCallback<T>((View) view, getPropertyInterceptor()));
        return this;
    }
    @Override
    public Binder<T> bindImageUrl(String property, Object imageView, Object imageLoader){
        if(!(imageView instanceof ImageView)){
            throw new IllegalArgumentException("the view must be ImageView");
        }
        if(!(imageLoader instanceof ViewHelper.IImageLoader)){
            throw new IllegalArgumentException("the loader must be  com.heaven7.core.util.ViewHelper.IImageLoader");
        }
        bind(property, new ImageUrlBinderCallback<T>((ImageView)imageView, getPropertyInterceptor(),
                (ViewHelper.IImageLoader) imageLoader));
        return this;
    }
    @Override
    public Binder<T> bindImageUri(String property, Object imageView){
        if(!(imageView instanceof ImageView)){
            throw new IllegalArgumentException("the view must be ImageView");
        }
        bind(property, new ImageUriBinderCallback<T>((ImageView) imageView, getPropertyInterceptor()));
        return this;
    }
    @Override
    public Binder<T> bindImageRes(String property, Object imageView){
        if(!(imageView instanceof ImageView)){
            throw new IllegalArgumentException("the view must be ImageView");
        }
        bind(property, new ImageResBinderCallback<T>((ImageView) imageView, getPropertyInterceptor()));
        return this;
    }
    @Override
    public Binder<T> bindImageDrawable(String property, Object imageView){
        if(!(imageView instanceof ImageView)){
            throw new IllegalArgumentException("the view must be ImageView");
        }
        bind(property, new ImageDrawableBinderCallback<T>((ImageView) imageView, getPropertyInterceptor()));
        return this;
    }
    @Override
    public Binder<T> bindImageBitmap(String property, Object imageView){
        if(!(imageView instanceof ImageView)){
            throw new IllegalArgumentException("the view must be ImageView");
        }
        bind(property, new ImageBitmapBinderCallback<T>((ImageView) imageView, getPropertyInterceptor()));
        return this;
    }
    @Override
    public Binder<T> bindRecyclerList(String property, Object recyclerView){
        if(!(recyclerView instanceof RecyclerView)){
            throw new IllegalArgumentException("the view must be RecyclerView");
        }
        final RecyclerView.Adapter adapter = ((RecyclerView)recyclerView).getAdapter();
        if(adapter == null || !(adapter instanceof BinderCallback)){
            throw new IllegalStateException("RecyclerView must set adapter and the adapter " +
                    "must impl BinderCallback !");
        }
        return bind(property, (BinderCallback<T>) adapter);
    }
    @Override
    public Binder<T> bindList(String property, Object listView){
        if(!(listView instanceof ListView)){
            throw new IllegalArgumentException("the view must be ListView");
        }
        final ListAdapter adapter = ((ListView)listView).getAdapter();
        if(adapter == null || !(adapter instanceof BinderCallback)){
            throw new IllegalStateException("ListView must set adapter and the adapter " +
                    "must impl BinderCallback !");
        }
        return bind(property, (BinderCallback<T>) adapter);
    }

    @Override
    public Binder<T> bindTextGravity(String property, Object textView) {
        if(!(textView instanceof TextView)){
            throw new IllegalArgumentException("must be TextView." );
        }
        return bind(property, new TextGravityCallback<T>((TextView) textView,
                getPropertyInterceptor()));
    }

    @Override
    public Binder<T> bindHintText(String property, Object textView) {
        if(!(textView instanceof TextView)){
            throw new IllegalArgumentException("must be TextView.");
        }
        return bind(property, new HintTextCallback<T>((TextView) textView,
                getPropertyInterceptor()));
    }

    @Override
    public Binder<T> bindHintTextRes(String property, Object textView) {
        if(!(textView instanceof TextView)){
            throw new IllegalArgumentException("must be TextView.");
        }
        return bind(property, new HintTextResCallback<T>((TextView) textView,
                getPropertyInterceptor()));
    }

    @Override
    public Binder<T> bindHintTextColor(String property, Object textView) {
        if(!(textView instanceof TextView)){
            throw new IllegalArgumentException("must be TextView.");
        }
        return bind(property, new HintTextColorCallback<T>((TextView) textView,
                getPropertyInterceptor()));
    }

    @Override
    public Binder<T> bindHintTextColorRes(String property, Object textView) {
        if(!(textView instanceof TextView)){
            throw new IllegalArgumentException("must be TextView.");
        }
        return bind(property, new HintTextColorResCallback<T>((TextView) textView,
                getPropertyInterceptor()));
    }

    @Override
    public Binder<T> bindHighlightColor(String property, Object textView) {
        if(!(textView instanceof TextView)){
            throw new IllegalArgumentException("must be TextView.");
        }
        return bind(property, new HighLightColorCallback<T>((TextView) textView,
                getPropertyInterceptor()));
    }

    @Override
    protected boolean shouldUseWeakMap() {
        return true;
    }
    //=================================== internal class ==========================
    private static class HighLightColorCallback<T> extends SimpleBinderCallback2<T>{
        public HighLightColorCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            ((TextView)view).setHighlightColor((Integer) newValue);
        }
    }
    private static class HintTextColorResCallback<T> extends SimpleBinderCallback2<T>{
        public HintTextColorResCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            ColorStateList list = view.getResources().getColorStateList((Integer) newValue);
            ((TextView)view).setHintTextColor(list);
        }
    }
    private static class HintTextColorCallback<T> extends SimpleBinderCallback2<T>{
        public HintTextColorCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            ((TextView)view).setHintTextColor((Integer) newValue);
        }
    }
    private static class HintTextResCallback<T> extends SimpleBinderCallback2<T>{
        public HintTextResCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            ((TextView)view).setHint((Integer) newValue);
        }
    }
    private static class HintTextCallback<T> extends SimpleBinderCallback2<T>{
        public HintTextCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            ((TextView)view).setHint((CharSequence) newValue);
        }
    }
    private static class TextGravityCallback<T> extends SimpleBinderCallback2<T>{
        public TextGravityCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            ((TextView)view).setGravity((Integer) newValue);
        }
    }
    private static class VisibilityBinderCallback<T> extends SimpleBinderCallback2<T>{

        final boolean mForceAsBoolean;

        public VisibilityBinderCallback(View tv, PropertyInterceptor interceptor,
                                        boolean forceAsBoolean) {
            super(tv, interceptor);
            this.mForceAsBoolean = forceAsBoolean;
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            if(mForceAsBoolean){
                view.setVisibility(Boolean.valueOf(newValue.toString())
                        ? View.VISIBLE : View.GONE);
            }else{
                view.setVisibility(Integer.valueOf(newValue.toString()));
            }
        }
    }

    private static class EnableBinderCallback<T> extends SimpleBinderCallback2<T> {
        public EnableBinderCallback(View tv, PropertyInterceptor interceptor) {
            super(tv,interceptor);
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            view.setEnabled((Boolean) newValue);
        }
    }
    private static class CheckableBinderCallback<T> extends SimpleBinderCallback2<T> {
        public CheckableBinderCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            ((Checkable) view).setChecked((Boolean) newValue);
        }
    }
    private static class ImageUriBinderCallback<T> extends SimpleBinderCallback2<T> {
        public ImageUriBinderCallback(ImageView tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            ((ImageView) view).setImageURI((Uri)newValue);
        }
    }
    private static class ImageBitmapBinderCallback<T> extends SimpleBinderCallback2<T> {
        public ImageBitmapBinderCallback(ImageView tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            ((ImageView) view).setImageBitmap((Bitmap) newValue);
        }
    }
    private static class ImageDrawableBinderCallback<T> extends SimpleBinderCallback2<T> {
        public ImageDrawableBinderCallback(ImageView tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            ((ImageView) view).setImageDrawable((Drawable) newValue);
        }
    }

    private static class ImageResBinderCallback<T> extends SimpleBinderCallback2<T> {
        public ImageResBinderCallback(ImageView tv,  PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            ((ImageView) view).setImageResource((Integer) newValue);
        }
    }
    private static class ImageUrlBinderCallback<T> extends SimpleBinderCallback2<T> {
        final ViewHelper.IImageLoader mLoader;
        public ImageUrlBinderCallback(View tv, PropertyInterceptor interceptor,
                                      ViewHelper.IImageLoader loader) {
            super(tv, interceptor);
            this.mLoader = loader;
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            mLoader.load((String) newValue, (ImageView) view);
        }
    }
    private static class BackgroundColorBinderCallback<T> extends SimpleBinderCallback2<T> {
        public BackgroundColorBinderCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            view.setBackgroundColor((Integer) newValue);
        }
    }
    private static class BackgroundBinderCallback<T> extends SimpleBinderCallback2<T> {
        public BackgroundBinderCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            ViewCompat.setBackground(view, (Drawable) newValue);
        }
    }
    private static class BackgroundResBinderCallback<T> extends SimpleBinderCallback2<T> {
        public BackgroundResBinderCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view, Object newValue) {
            int resId = Integer.valueOf(newValue.toString());
            view.setBackgroundResource(resId);
        }
    }
    private static class TextBinderCallback<T> extends SimpleBinderCallback2<T> {
        public TextBinderCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view,  Object newValue) {
            ((TextView)view).setText(String.valueOf(newValue));
        }
    }
    private static class TextResBinderCallback<T> extends SimpleBinderCallback2<T> {
        public TextResBinderCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view,  Object newValue) {
            ((TextView)view).setText(view.getResources()
                    .getString((Integer) newValue));
        }
    }
    private static class TextSizeResBinderCallback<T> extends SimpleBinderCallback2<T> {
        public TextSizeResBinderCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view,  Object newValue) {
            ((TextView)view).setTextSize(TypedValue.COMPLEX_UNIT_PX,
                    view.getResources().getDimensionPixelSize((Integer) newValue));
        }
    }
    private static class TextSizeDpBinderCallback<T> extends SimpleBinderCallback2<T> {
        public TextSizeDpBinderCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view,  Object newValue) {
            ((TextView)view).setTextSize(Float.valueOf(newValue.toString()));
        }
    }
    private static class TextSizeBinderCallback<T> extends SimpleBinderCallback2<T> {
        public TextSizeBinderCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view,  Object newValue) {
            ((TextView)view).setTextSize(TypedValue.COMPLEX_UNIT_PX,
                    Float.valueOf(newValue.toString()));
        }
    }
    private static class TextColorBinderCallback<T> extends SimpleBinderCallback2<T> {
        public TextColorBinderCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view,  Object newValue) {
            if(newValue != null) {
                ((TextView) view).setTextColor((Integer) newValue);
            }
        }
    }
    private static class TextColorResBinderCallback<T> extends SimpleBinderCallback2<T> {
        public TextColorResBinderCallback(View tv, PropertyInterceptor interceptor) {
            super(tv, interceptor);
        }
        @Override
        protected void apply(Property prop, View view,  Object newValue) {
            ((TextView) view).setTextColor(
                    view.getResources().getColor((Integer) newValue));
        }
    }

}


text:
require 'zip'
require 'nokogiri'
require 'tempfile'

Zip.on_exists_proc = true

module Mlatr
  class Document
    attr_reader :document, :word_zip, :styles
    attr_accessor :author, :instructor, :class_title, :date, :title, :body, :works_cited

    def initialize(path, &block)
      @word_zip = Zip::File.open path

      @document = Nokogiri::XML @word_zip.read 'word/document.xml'
      @styles = @word_zip.read 'word/styles.xml'

      parse

      if block_given?
        yield self
        @word_zip.close
      end

      self
    end

    # Returns an IO object for the thumbnail.
    def thumbnail
      img = Tempfile.new 'thumbnail.jpeg'
      @word_zip.extract 'docProps/thumbnail.jpeg', img
      img
    end

    def self.open(path, &block)
      self.new(path, &block)
    end

    private
    def parse
      paragraphs = @document.xpath('//w:document//w:body//w:p').map do |p|
        p.xpath('.//w:t').map { |t| t.text }.join ''
      end

      parse_author(paragraphs)
      parse_instructor(paragraphs)
      parse_class_title(paragraphs)
      parse_date(paragraphs)
      parse_title(paragraphs)
      parse_body(paragraphs)
      parse_works_cited(paragraphs)
    end

    def parse_author(paragraphs)
      @author = paragraphs[0].to_s
    end

    def parse_instructor(paragraphs)
      @instructor = paragraphs[1].to_s
    end

    def parse_class_title(paragraphs)
      @class_title = paragraphs[2].to_s
    end

    def parse_date(paragraphs)
      @date = paragraphs[3].to_s
    end

    def parse_title(paragraphs)
      @title = paragraphs[4].to_s
    end

    def parse_body(paragraphs)
      body = []

      paragraphs.drop(5).each do |p|
        if p === "Works Cited"
          break
        elsif p.empty?
          next
        else
          body << p
        end

      end

      @body = body.join "\n"
    end

    def parse_works_cited(paragraphs)
    end
  end
end


text:
<?php
namespace Logger\Formatters;

use Logger\Common\FormatterTestCase;
use Psr\Log\LogLevel;

class CallbackFormatterTest extends FormatterTestCase {
	public function test(): void {
		$testLogger = $this->createTestLogger();
		$logger = new CallbackFormatter($testLogger, function (string $level, string $message, array $context) {
			return (string) json_encode(['lvl' => $level, 'msg' => $message]);
		});
		$logger->log(LogLevel::DEBUG, 'This is a test');
		self::assertEquals('{"lvl":"debug","msg":"This is a test"}', $testLogger->getLastLine()->getMessage());
	}
}


text:
//
//  New Relic for Mobile -- iOS edition
//
//  See:
//    https://docs.newrelic.com/docs/mobile-apps for information
//    https://docs.newrelic.com/docs/releases/ios for release notes
//
//  Copyright (c) 2014 New Relic. All rights reserved.
//  See https://docs.newrelic.com/docs/licenses/ios-agent-licenses for license details
//

#import <Foundation/Foundation.h>

/*!
 NRMAFeatureFlags

 These flags are used to identify New Relic features.

 - NRFeatureFlag_NSURLSessionInstrumentation
    Disabled by default. Flag for instrumentation of NSURLSessions.
    Currently only instruments network activity dispatched with
    NSURLSessionDataTasks and NSURLSessionUploadTasks.

- NRFeatureFlag_ExperimentalNetworkingInstrumentation
   Disabled by default. Enables experimental networking instrumentation. This
   feature may decrease the stability of applications.

- NRFeatureFlag_SwifterInteractionTracing
   Beware: enabling this feature may cause your swift application to crash.
   please read https://docs.newrelic.com/docs/mobile-monitoring/new-relic-mobile/getting-started/enabling-interaction-tracing-swift
   before enabling this feature.

- NRFeatureFlag_DefaultInteractions
    Enabled by default. This flag is used to only disable the default Interactions
    New Relic will trace. Default interactions are started when a view controller is displayed
    and are titled "Displayed <ViewControllerName>". This flag is associated with
    NRFeatureFlag_InteractionTracing, but acts as a subset of functionality on that feature.
*/

typedef NS_OPTIONS(unsigned long long, NRMAFeatureFlags){
    NRFeatureFlag_InteractionTracing                    = 1 << 1,
    NRFeatureFlag_SwiftInteractionTracing               = 1 << 2, //disabled by default
    NRFeatureFlag_CrashReporting                        = 1 << 3,
    NRFeatureFlag_NSURLSessionInstrumentation           = 1 << 4,
    NRFeatureFlag_HttpResponseBodyCapture               = 1 << 5,
    NRFeatureFlag_GestureInstrumentation                = 1 << 6,
    NRFeatureFlag_DefaultInteractions                   = 1 << 12,
    NRFeatureFlag_ExperimentalNetworkingInstrumentation = 1 << 13, //disabled by default
    NRFeatureFlag_AllFeatures                           = ~0ULL //in 32-bit land the alignment is 4bytes
};


text:
#include <linux/module.h>
#include <linux/i2o.h>
#include <linux/delay.h>
#include <linux/workqueue.h>
#include <linux/string.h>
#include <linux/slab.h>
#include <linux/sched.h>	/* wait_event_interruptible_timeout() needs this */
#include <asm/param.h>		/* HZ */
#include "core.h"

#define OSM_NAME "exec-osm"

struct i2o_driver i2o_exec_driver;

static int i2o_exec_lct_notify(struct i2o_controller *c, u32 change_ind);

/* global wait list for POST WAIT */
static LIST_HEAD(i2o_exec_wait_list);

/* Wait struct needed for POST WAIT */
struct i2o_exec_wait {
	wait_queue_head_t *wq;	/* Pointer to Wait queue */
	struct i2o_dma dma;	/* DMA buffers to free on failure */
	u32 tcntxt;		/* transaction context from reply */
	int complete;		/* 1 if reply received otherwise 0 */
	u32 m;			/* message id */
	struct i2o_message *msg;	/* pointer to the reply message */
	struct list_head list;	/* node in global wait list */
};

/* Exec OSM class handling definition */
static struct i2o_class_id i2o_exec_class_id[] = {
	{I2O_CLASS_EXECUTIVE},
	{I2O_CLASS_END}
};

/**
 *	i2o_exec_wait_alloc - Allocate a i2o_exec_wait struct an initialize it
 *
 *	Allocate the i2o_exec_wait struct and initialize the wait.
 *
 *	Returns i2o_exec_wait pointer on success or negative error code on
 *	failure.
 */
static struct i2o_exec_wait *i2o_exec_wait_alloc(void)
{
	struct i2o_exec_wait *wait;

	wait = kzalloc(sizeof(*wait), GFP_KERNEL);
	if (!wait)
		return NULL;

	INIT_LIST_HEAD(&wait->list);

	return wait;
};

/**
 *	i2o_exec_wait_free - Free a i2o_exec_wait struct
 *	@i2o_exec_wait: I2O wait data which should be cleaned up
 */
static void i2o_exec_wait_free(struct i2o_exec_wait *wait)
{
	kfree(wait);
};

/**
 * 	i2o_msg_post_wait_mem - Post and wait a message with DMA buffers
 *	@c: controller
 *	@m: message to post
 *	@timeout: time in seconds to wait
 *	@dma: i2o_dma struct of the DMA buffer to free on failure
 *
 * 	This API allows an OSM to post a message and then be told whether or
 *	not the system received a successful reply. If the message times out
 *	then the value '-ETIMEDOUT' is returned. This is a special case. In
 *	this situation the message may (should) complete at an indefinite time
 *	in the future. When it completes it will use the memory buffer
 *	attached to the request. If -ETIMEDOUT is returned then the memory
 *	buffer must not be freed. Instead the event completion will free them
 *	for you. In all other cases the buffer are your problem.
 *
 *	Returns 0 on success, negative error code on timeout or positive error
 *	code from reply.
 */
int i2o_msg_post_wait_mem(struct i2o_controller *c, struct i2o_message *msg,
			  unsigned long timeout, struct i2o_dma *dma)
{
	DECLARE_WAIT_QUEUE_HEAD(wq);
	struct i2o_exec_wait *wait;
	static u32 tcntxt = 0x80000000;
	int rc = 0;

	wait = i2o_exec_wait_alloc();
	if (!wait)
		return -ENOMEM;

	if (tcntxt == 0xffffffff)
		tcntxt = 0x80000000;

	if (dma)
		wait->dma = *dma;

	/*
	 * Fill in the message initiator context and transaction context.
	 * We will only use transaction contexts >= 0x80000000 for POST WAIT,
	 * so we could find a POST WAIT reply easier in the reply handler.
	 */
	msg->u.s.icntxt = cpu_to_le32(i2o_exec_driver.context);
	wait->tcntxt = tcntxt++;
	msg->u.s.tcntxt = cpu_to_le32(wait->tcntxt);

	/*
	 * Post the message to the controller. At some point later it will
	 * return. If we time out before it returns then complete will be zero.
	 */
	i2o_msg_post(c, msg);

	if (!wait->complete) {
		wait->wq = &wq;
		/*
		 * we add elements add the head, because if a entry in the list
		 * will never be removed, we have to iterate over it every time
		 */
		list_add(&wait->list, &i2o_exec_wait_list);

		wait_event_interruptible_timeout(wq, wait->complete,
						 timeout * HZ);

		wait->wq = NULL;
	}

	barrier();

	if (wait->complete) {
		rc = le32_to_cpu(wait->msg->body[0]) >> 24;
		i2o_flush_reply(c, wait->m);
		i2o_exec_wait_free(wait);
	} else {
		/*
		 * We cannot remove it now. This is important. When it does
		 * terminate (which it must do if the controller has not
		 * died...) then it will otherwise scribble on stuff.
		 *
		 * FIXME: try abort message
		 */
		if (dma)
			dma->virt = NULL;

		rc = -ETIMEDOUT;
	}

	return rc;
};

/**
 *	i2o_msg_post_wait_complete - Reply to a i2o_msg_post request from IOP
 *	@c: I2O controller which answers
 *	@m: message id
 *	@msg: pointer to the I2O reply message
 *	@context: transaction context of request
 *
 *	This function is called in interrupt context only. If the reply reached
 *	before the timeout, the i2o_exec_wait struct is filled with the message
 *	and the task will be waked up. The task is now responsible for returning
 *	the message m back to the controller! If the message reaches us after
 *	the timeout clean up the i2o_exec_wait struct (including allocated
 *	DMA buffer).
 *
 *	Return 0 on success and if the message m should not be given back to the
 *	I2O controller, or >0 on success and if the message should be given back
 *	afterwords. Returns negative error code on failure. In this case the
 *	message must also be given back to the controller.
 */
static int i2o_msg_post_wait_complete(struct i2o_controller *c, u32 m,
				      struct i2o_message *msg, u32 context)
{
	struct i2o_exec_wait *wait, *tmp;
	unsigned long flags;
	static spinlock_t lock = SPIN_LOCK_UNLOCKED;
	int rc = 1;

	/*
	 * We need to search through the i2o_exec_wait_list to see if the given
	 * message is still outstanding. If not, it means that the IOP took
	 * longer to respond to the message than we had allowed and timer has
	 * already expired. Not much we can do about that except log it for
	 * debug purposes, increase timeout, and recompile.
	 */
	spin_lock_irqsave(&lock, flags);
	list_for_each_entry_safe(wait, tmp, &i2o_exec_wait_list, list) {
		if (wait->tcntxt == context) {
			list_del(&wait->list);

			spin_unlock_irqrestore(&lock, flags);

			wait->m = m;
			wait->msg = msg;
			wait->complete = 1;

			barrier();

			if (wait->wq) {
				wake_up_interruptible(wait->wq);
				rc = 0;
			} else {
				struct device *dev;

				dev = &c->pdev->dev;

				pr_debug("%s: timedout reply received!\n",
					 c->name);
				i2o_dma_free(dev, &wait->dma);
				i2o_exec_wait_free(wait);
				rc = -1;
			}

			return rc;
		}
	}

	spin_unlock_irqrestore(&lock, flags);

	osm_warn("%s: Bogus reply in POST WAIT (tr-context: %08x)!\n", c->name,
		 context);

	return -1;
};

/**
 *	i2o_exec_show_vendor_id - Displays Vendor ID of controller
 *	@d: device of which the Vendor ID should be displayed
 *	@buf: buffer into which the Vendor ID should be printed
 *
 *	Returns number of bytes printed into buffer.
 */
static ssize_t i2o_exec_show_vendor_id(struct device *d,
				       struct device_attribute *attr, char *buf)
{
	struct i2o_device *dev = to_i2o_device(d);
	u16 id;

	if (!i2o_parm_field_get(dev, 0x0000, 0, &id, 2)) {
		sprintf(buf, "0x%04x", le16_to_cpu(id));
		return strlen(buf) + 1;
	}

	return 0;
};

/**
 *	i2o_exec_show_product_id - Displays Product ID of controller
 *	@d: device of which the Product ID should be displayed
 *	@buf: buffer into which the Product ID should be printed
 *
 *	Returns number of bytes printed into buffer.
 */
static ssize_t i2o_exec_show_product_id(struct device *d,
					struct device_attribute *attr,
					char *buf)
{
	struct i2o_device *dev = to_i2o_device(d);
	u16 id;

	if (!i2o_parm_field_get(dev, 0x0000, 1, &id, 2)) {
		sprintf(buf, "0x%04x", le16_to_cpu(id));
		return strlen(buf) + 1;
	}

	return 0;
};

/* Exec-OSM device attributes */
static DEVICE_ATTR(vendor_id, S_IRUGO, i2o_exec_show_vendor_id, NULL);
static DEVICE_ATTR(product_id, S_IRUGO, i2o_exec_show_product_id, NULL);

/**
 *	i2o_exec_probe - Called if a new I2O device (executive class) appears
 *	@dev: I2O device which should be probed
 *
 *	Registers event notification for every event from Executive device. The
 *	return is always 0, because we want all devices of class Executive.
 *
 *	Returns 0 on success.
 */
static int i2o_exec_probe(struct device *dev)
{
	struct i2o_device *i2o_dev = to_i2o_device(dev);
	struct i2o_controller *c = i2o_dev->iop;

	i2o_event_register(i2o_dev, &i2o_exec_driver, 0, 0xffffffff);

	c->exec = i2o_dev;

	i2o_exec_lct_notify(c, c->lct->change_ind + 1);

	device_create_file(dev, &dev_attr_vendor_id);
	device_create_file(dev, &dev_attr_product_id);

	return 0;
};

/**
 *	i2o_exec_remove - Called on I2O device removal
 *	@dev: I2O device which was removed
 *
 *	Unregisters event notification from Executive I2O device.
 *
 *	Returns 0 on success.
 */
static int i2o_exec_remove(struct device *dev)
{
	device_remove_file(dev, &dev_attr_product_id);
	device_remove_file(dev, &dev_attr_vendor_id);

	i2o_event_register(to_i2o_device(dev), &i2o_exec_driver, 0, 0);

	return 0;
};

/**
 *	i2o_exec_lct_modified - Called on LCT NOTIFY reply
 *	@c: I2O controller on which the LCT has modified
 *
 *	This function handles asynchronus LCT NOTIFY replies. It parses the
 *	new LCT and if the buffer for the LCT was to small sends a LCT NOTIFY
 *	again, otherwise send LCT NOTIFY to get informed on next LCT change.
 */
static void i2o_exec_lct_modified(struct i2o_controller *c)
{
	u32 change_ind = 0;

	if (i2o_device_parse_lct(c) != -EAGAIN)
		change_ind = c->lct->change_ind + 1;

#ifdef CONFIG_I2O_LCT_NOTIFY_ON_CHANGES
	i2o_exec_lct_notify(c, change_ind);
#endif
};

/**
 *	i2o_exec_reply -  I2O Executive reply handler
 *	@c: I2O controller from which the reply comes
 *	@m: message id
 *	@msg: pointer to the I2O reply message
 *
 *	This function is always called from interrupt context. If a POST WAIT
 *	reply was received, pass it to the complete function. If a LCT NOTIFY
 *	reply was received, a new event is created to handle the update.
 *
 *	Returns 0 on success and if the reply should not be flushed or > 0
 *	on success and if the reply should be flushed. Returns negative error
 *	code on failure and if the reply should be flushed.
 */
static int i2o_exec_reply(struct i2o_controller *c, u32 m,
			  struct i2o_message *msg)
{
	u32 context;

	if (le32_to_cpu(msg->u.head[0]) & MSG_FAIL) {
		struct i2o_message __iomem *pmsg;
		u32 pm;

		/*
		 * If Fail bit is set we must take the transaction context of
		 * the preserved message to find the right request again.
		 */

		pm = le32_to_cpu(msg->body[3]);
		pmsg = i2o_msg_in_to_virt(c, pm);
		context = readl(&pmsg->u.s.tcntxt);

		i2o_report_status(KERN_INFO, "i2o_core", msg);

		/* Release the preserved msg */
		i2o_msg_nop_mfa(c, pm);
	} else
		context = le32_to_cpu(msg->u.s.tcntxt);

	if (context & 0x80000000)
		return i2o_msg_post_wait_complete(c, m, msg, context);

	if ((le32_to_cpu(msg->u.head[1]) >> 24) == I2O_CMD_LCT_NOTIFY) {
		struct work_struct *work;

		pr_debug("%s: LCT notify received\n", c->name);

		work = kmalloc(sizeof(*work), GFP_ATOMIC);
		if (!work)
			return -ENOMEM;

		INIT_WORK(work, (void (*)(void *))i2o_exec_lct_modified, c);
		queue_work(i2o_exec_driver.event_queue, work);
		return 1;
	}

	/*
	 * If this happens, we want to dump the message to the syslog so
	 * it can be sent back to the card manufacturer by the end user
	 * to aid in debugging.
	 *
	 */
	printk(KERN_WARNING "%s: Unsolicited message reply sent to core!"
	       "Message dumped to syslog\n", c->name);
	i2o_dump_message(msg);

	return -EFAULT;
}

/**
 *	i2o_exec_event - Event handling function
 *	@evt: Event which occurs
 *
 *	Handles events send by the Executive device. At the moment does not do
 *	anything useful.
 */
static void i2o_exec_event(struct i2o_event *evt)
{
	if (likely(evt->i2o_dev))
		osm_debug("Event received from device: %d\n",
			  evt->i2o_dev->lct_data.tid);
	kfree(evt);
};

/**
 *	i2o_exec_lct_get - Get the IOP's Logical Configuration Table
 *	@c: I2O controller from which the LCT should be fetched
 *
 *	Send a LCT NOTIFY request to the controller, and wait
 *	I2O_TIMEOUT_LCT_GET seconds until arrival of response. If the LCT is
 *	to large, retry it.
 *
 *	Returns 0 on success or negative error code on failure.
 */
int i2o_exec_lct_get(struct i2o_controller *c)
{
	struct i2o_message *msg;
	int i = 0;
	int rc = -EAGAIN;

	for (i = 1; i <= I2O_LCT_GET_TRIES; i++) {
		msg = i2o_msg_get_wait(c, I2O_TIMEOUT_MESSAGE_GET);
		if (IS_ERR(msg))
			return PTR_ERR(msg);

		msg->u.head[0] =
		    cpu_to_le32(EIGHT_WORD_MSG_SIZE | SGL_OFFSET_6);
		msg->u.head[1] =
		    cpu_to_le32(I2O_CMD_LCT_NOTIFY << 24 | HOST_TID << 12 |
				ADAPTER_TID);
		msg->body[0] = cpu_to_le32(0xffffffff);
		msg->body[1] = cpu_to_le32(0x00000000);
		msg->body[2] = cpu_to_le32(0xd0000000 | c->dlct.len);
		msg->body[3] = cpu_to_le32(c->dlct.phys);

		rc = i2o_msg_post_wait(c, msg, I2O_TIMEOUT_LCT_GET);
		if (rc < 0)
			break;

		rc = i2o_device_parse_lct(c);
		if (rc != -EAGAIN)
			break;
	}

	return rc;
}

/**
 *	i2o_exec_lct_notify - Send a asynchronus LCT NOTIFY request
 *	@c: I2O controller to which the request should be send
 *	@change_ind: change indicator
 *
 *	This function sends a LCT NOTIFY request to the I2O controller with
 *	the change indicator change_ind. If the change_ind == 0 the controller
 *	replies immediately after the request. If change_ind > 0 the reply is
 *	send after change indicator of the LCT is > change_ind.
 */
static int i2o_exec_lct_notify(struct i2o_controller *c, u32 change_ind)
{
	i2o_status_block *sb = c->status_block.virt;
	struct device *dev;
	struct i2o_message *msg;

	dev = &c->pdev->dev;

	if (i2o_dma_realloc
	    (dev, &c->dlct, le32_to_cpu(sb->expected_lct_size), GFP_KERNEL))
		return -ENOMEM;

	msg = i2o_msg_get_wait(c, I2O_TIMEOUT_MESSAGE_GET);
	if (IS_ERR(msg))
		return PTR_ERR(msg);

	msg->u.head[0] = cpu_to_le32(EIGHT_WORD_MSG_SIZE | SGL_OFFSET_6);
	msg->u.head[1] = cpu_to_le32(I2O_CMD_LCT_NOTIFY << 24 | HOST_TID << 12 |
				     ADAPTER_TID);
	msg->u.s.icntxt = cpu_to_le32(i2o_exec_driver.context);
	msg->u.s.tcntxt = cpu_to_le32(0x00000000);
	msg->body[0] = cpu_to_le32(0xffffffff);
	msg->body[1] = cpu_to_le32(change_ind);
	msg->body[2] = cpu_to_le32(0xd0000000 | c->dlct.len);
	msg->body[3] = cpu_to_le32(c->dlct.phys);

	i2o_msg_post(c, msg);

	return 0;
};

/* Exec OSM driver struct */
struct i2o_driver i2o_exec_driver = {
	.name = OSM_NAME,
	.reply = i2o_exec_reply,
	.event = i2o_exec_event,
	.classes = i2o_exec_class_id,
	.driver = {
		   .probe = i2o_exec_probe,
		   .remove = i2o_exec_remove,
		   },
};

/**
 *	i2o_exec_init - Registers the Exec OSM
 *
 *	Registers the Exec OSM in the I2O core.
 *
 *	Returns 0 on success or negative error code on failure.
 */
int __init i2o_exec_init(void)
{
	return i2o_driver_register(&i2o_exec_driver);
};

/**
 *	i2o_exec_exit - Removes the Exec OSM
 *
 *	Unregisters the Exec OSM from the I2O core.
 */
void __exit i2o_exec_exit(void)
{
	i2o_driver_unregister(&i2o_exec_driver);
};

EXPORT_SYMBOL(i2o_msg_post_wait_mem);
EXPORT_SYMBOL(i2o_exec_lct_get);